WooCommerce: как отключить просмотр и доступ к разделам товаров для определённых ролей пользователей

Диагностика задачи: зачем ограничивать доступ к разделам товаров по ролям

В WooCommerce нередко возникает необходимость скрыть определённые категории или товары от конкретных групп пользователей. Задача может быть связана с оптовыми покупателями, внутренними сотрудниками или гостями. Например, администраторы хотят, чтобы обычные пользователи не видели товары для оптовиков или внутренний каталог.

Стандартных настроек WooCommerce для этого нет, поэтому приходится использовать программные решения. Важно понять, что необходимо ограничить не только визуальный показ, но и прямой доступ по URL, а также исключить товары из поиска и виджетов.

Пошаговое решение: скрываем категории и товары по ролям

1. Определение ролей и категорий для ограничения

Для начала уточним, какие роли пользователей мы хотим ограничить и какие категории скрыть. Например, мы хотим скрыть категорию с ярлыком wholesale для всех пользователей, у которых нет роли wholesale_customer.

2. Фильтрация запросов WooCommerce

Добавим фильтр, который исключит товары из категории wholesale для неподходящих пользователей. Код вставляем в файл functions.php дочерней темы или в собственный плагин:

add_action('pre_get_posts', function($query) {
    if (is_admin() || !$query->is_main_query()) {
        return;
    }
    if (is_shop() || is_product_category() || is_product_tag()) {
        $user = wp_get_current_user();
        // Проверяем роль пользователя
        if (!in_array('wholesale_customer', (array) $user->roles)) {
            // Получаем ID категории wholesale
            $term = get_term_by('slug', 'wholesale', 'product_cat');
            if ($term) {
                $tax_query = (array) $query->get('tax_query');
                $tax_query[] = array(
                    'taxonomy' => 'product_cat',
                    'field' => 'term_id',
                    'terms' => array($term->term_id),
                    'operator' => 'NOT IN',
                );
                $query->set('tax_query', $tax_query);
            }
        }
    }
});

3. Блокировка прямого доступа к товарам из скрытой категории

Чтобы пользователь не мог перейти по прямой ссылке на товар из категории wholesale, добавим проверку на загрузке страницы одиночного товара:

add_action('template_redirect', function() {
    if (is_singular('product')) {
        $user = wp_get_current_user();
        if (!in_array('wholesale_customer', (array) $user->roles)) {
            global $post;
            $terms = get_the_terms($post->ID, 'product_cat');
            if ($terms) {
                foreach ($terms as $term) {
                    if ($term->slug === 'wholesale') {
                        wp_redirect(home_url());
                        exit;
                    }
                }
            }
        }
    }
});

Проверка результата после внедрения

  • Создайте тестового пользователя с ролью, отличной от wholesale_customer.
  • Зайдите под этим пользователем на страницу магазина и убедитесь, что товары из категории wholesale не отображаются.
  • Попробуйте перейти по прямой ссылке на товар из категории wholesale — должен произойти редирект на главную или страницу по вашему выбору.
  • Авторизуйтесь под пользователем с ролью wholesale_customer и проверьте, что товары видны.

Частые ошибки и способы их устранения

  • Не работает фильтрация в админке. Фильтр pre_get_posts применён с условием is_admin() — убедитесь, что вы не исключаете запросы в админке, если там хотите видеть все товары.
  • Редирект на странице товара не срабатывает. Проверьте, что хук template_redirect не конфликтует с другими плагинами или темой, и что проверка категорий выполнена корректно.
  • Товары отображаются в виджетах поиска или рекомендованных товаров. Для полного скрытия нужно дополнительно фильтровать запросы виджетов и поиск, например, через woocommerce_product_query.

Практические советы по безопасности и производительности

  • Обрабатывайте роли пользователей с помощью wp_get_current_user(), не полагаясь на глобальные переменные.
  • Проверяйте наличие категорий через get_term_by и кешируйте результат, если возможно.
  • Используйте минимально необходимые хуки и не загружайте лишние проверки на страницах, где они не нужны.
  • Если сайт большой, подумайте об использовании transient-кеша для результатов проверки ролей и категорий.

Сравнение способов ограничения доступа к товарам

МетодПлюсыМинусыКомпромисс
Плагин для ограничения контентаУдобство настройки, готовые функцииНагрузка, лишний функционал, зависимость от стороннего кодаИспользовать легковесные плагины, проверенные сообществом
Кодовые фильтры в functions.phpЛёгкий, контролируемый, без сторонних зависимостейНужно уметь программировать, требуется поддержкаПисать аккуратный, хорошо документированный код
Комбинированный подходГибкость, можно быстро внедрить и доработатьРиск конфликтов, требует тестированияТестировать на тестовом окружении перед продакшеном
WooCommerce: автоматическое изменение статуса заказа при отключении метода оплаты
30.06.2026
Как избежать проблемы выхода из аккаунта WordPress при использовании кеш-подключений
26.02.2026
WooCommerce: решение проблемы с отображением товаров после обновления кеша
11.05.2026
Как сделать вывод постов по таксономии с мета полями в WordPress
02.03.2026
WordPress: как удалить версии постов из базы данных
11.11.2025