WooCommerce: автоматическое изменение стоимости товаров по ролям пользователей

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

В интернет-магазинах на WooCommerce часто возникает задача предоставить разные цены для разных групп покупателей: оптовиков, постоянных клиентов, партнеров. Это позволяет гибко управлять ценовой политикой без необходимости создавать отдельные товары или использовать отдельные магазины.

Основные признаки необходимости автоматического изменения цен:

  • Разные цены должны показываться уже на странице товара и в корзине;
  • Необходимо сохранить простоту управления товарами без дублирования записей;
  • Цена должна корректно отображаться для гостей и зарегистрированных пользователей с разными ролями;
  • Изменения в цене должны учитывать скидки и акции WooCommerce.

Как реализовать изменение цены товаров по ролям пользователей в WooCommerce

Подключение пользовательских ролей

Для начала убедимся, что у вас существуют нужные роли пользователей. Если необходимо, создайте их в functions.php или через плагин. Пример добавления роли:

add_role('wholesaler', 'Оптовик', array(
    'read' => true,
    'level_0' => true
));

Фильтрация цены товара на фронтенде

Основной метод — использовать фильтр woocommerce_product_get_price и woocommerce_product_get_regular_price для изменения цены товара в зависимости от роли пользователя.

function change_price_by_user_role($price, $product) {
    if (is_admin()) return $price;

    if (!is_user_logged_in()) return $price; // цена для гостей

    $user = wp_get_current_user();
    if (in_array('wholesaler', (array) $user->roles)) {
        // уменьшаем цену на 20% для оптовиков
        $price = $price * 0.8;
    } elseif (in_array('vip_customer', (array) $user->roles)) {
        // уменьшаем цену на 10% для VIP клиентов
        $price = $price * 0.9;
    }
    return $price;
}
add_filter('woocommerce_product_get_price', 'change_price_by_user_role', 10, 2);
add_filter('woocommerce_product_get_regular_price', 'change_price_by_user_role', 10, 2);

Этот код применит скидку к цене товара в каталоге и на странице товара для пользователей с определёнными ролями.

Изменение цены в корзине и оформлении заказа

Чтобы скидка корректно применялась в корзине и на этапе оформления, нужно использовать фильтр woocommerce_before_calculate_totals для изменения цены в объекте товара корзины:

function apply_role_based_price_cart($cart) {
    if (is_admin() && !defined('DOING_AJAX')) return;

    if (!is_user_logged_in()) return;

    $user = wp_get_current_user();

    foreach ($cart->get_cart() as $cart_item) {
        $product = $cart_item['data'];
        $original_price = $product->get_regular_price();

        if (in_array('wholesaler', (array) $user->roles)) {
            $new_price = $original_price * 0.8;
        } elseif (in_array('vip_customer', (array) $user->roles)) {
            $new_price = $original_price * 0.9;
        } else {
            $new_price = $original_price;
        }

        $product->set_price($new_price);
    }
}
add_action('woocommerce_before_calculate_totals', 'apply_role_based_price_cart', 10, 1);

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

  • Залогиньтесь под пользователем с ролью wholesaler и убедитесь, что цены на странице товара и в каталоге отображаются с 20% скидкой.
  • Проверьте корзину и оформление заказа — цена товара должна сохраняться со скидкой.
  • Выйдите из системы или залогиньтесь как обычный пользователь, чтобы проверить, что цены отображаются без изменений.
  • Проверьте работу с разными товарами (простой, вариативный), чтобы убедиться, что скидки применяются корректно.

Частые ошибки и как их исправить

  • Цены не меняются на странице товара — проверьте, что фильтры применяются корректно и не переписываются другими плагинами. Используйте var_dump и логи для отладки.
  • Скидка не применяется в корзине — убедитесь, что функция hooked к woocommerce_before_calculate_totals и не раннее.
  • Конфликт с кешированием — кеш может показывать цены без скидок. Настройте исключения по ролям для кеша или используйте динамические блоки.
  • Цена в заказах и отчетах не совпадает — всегда меняйте цену через объект товара корзины, а не напрямую в базе или метаданных.

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

  • Избегайте повторных расчетов: кешируйте рассчитанные цены в сессии или метаданных пользователя.
  • Проверяйте права пользователя через current_user_can() для более гибкой настройки ролей.
  • Помните, что изменение цены через фильтры не меняет цену в базе, поэтому отчеты WooCommerce могут показывать оригинальные цены.
  • Тестируйте на staging-сайте и убедитесь, что ваши изменения не конфликтуют с активными плагинами безопасности и кеширования.

Сравнение способов реализации изменения цены по ролям

МетодПлюсыМинусыПрименение
Фильтры WooCommerce (код)Гибко, бесплатно, не требует плагиновТребует навыков, может конфликтоватьДля кастомных решений
Плагины (например, "WooCommerce Role Based Pricing")Просто установить и настроитьПлатные, могут грузить сайтДля быстрого запуска без кода
Создание отдельных товаров/каталоговПростая логикаДублирование товаров, сложность администрированияРедкие случаи, сложные каталоги
Как создать функцию автоматической отправки Email в WordPress с примерами кода
21.03.2026
Как удалить CSS и JS файлы в WordPress правильно
09.12.2025
WooCommerce: как автоматически удалять товар из корзины после оплаты
10.06.2026
WooCommerce: установка ограничений на количество товаров в корзине
10.05.2026
Автоматическое удаление старых записей в WordPress через WP-Cron с примерами кода
05.02.2026