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

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

В WooCommerce часто возникает необходимость применять разные скидки к товарам в разных категориях. Например, на одну категорию действует скидка 10%, на другую — 20%. Если товаров много, вручную менять цены неудобно и рискованно с точки зрения ошибок. Задача — реализовать автоматическое изменение цены товара при отображении на сайте и в корзине, без постоянного редактирования каждой позиции.

Проверяем, что именно нужно:

  • Скидка должна применяться динамически, без изменения базовой цены товара в админке.
  • Цена на странице товара, в каталоге и в корзине должна показываться уже со скидкой.
  • Поддержка разных процентов скидки для категорий.
  • Отслеживание правильности отображения в заказах и отчетах.

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

1. Определяем категории и соответствующие скидки

Создадим массив с категориями и скидками в процентах. Например:

function get_category_discounts() {
    return [
        'sale-category' => 10,  // категория 'sale-category' со скидкой 10%
        'clearance' => 20,    // категория 'clearance' со скидкой 20%
    ];
}

2. Изменяем цену товара на лету с помощью фильтра woocommerce_product_get_price

Добавим функцию, которая проверит категории товара и применит нужную скидку:

add_filter('woocommerce_product_get_price', 'custom_category_based_price', 10, 2);
add_filter('woocommerce_product_get_regular_price', 'custom_category_based_price', 10, 2);

function custom_category_based_price($price, $product) {
    $discounts = get_category_discounts();
    $categories = wp_get_post_terms($product->get_id(), 'product_cat', ['fields' => 'slugs']);

    foreach ($categories as $cat_slug) {
        if (isset($discounts[$cat_slug])) {
            $discount_percent = $discounts[$cat_slug];
            $price = $price * (1 - $discount_percent / 100);
            break; // Применяем первую найденную категорию со скидкой
        }
    }
    return round($price, 2);
}

3. Обновляем цену для корзины и заказов

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

add_action('woocommerce_before_calculate_totals', 'custom_category_price_cart', 10, 1);

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

    $discounts = get_category_discounts();

    foreach ($cart->get_cart() as $cart_item_key => $cart_item) {
        $product = $cart_item['data'];
        $categories = wp_get_post_terms($product->get_id(), 'product_cat', ['fields' => 'slugs']);

        foreach ($categories as $cat_slug) {
            if (isset($discounts[$cat_slug])) {
                $discount_percent = $discounts[$cat_slug];
                $new_price = $product->get_regular_price() * (1 - $discount_percent / 100);
                $product->set_price(round($new_price, 2));
                break;
            }
        }
    }
}

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

  • Перейдите на страницу каталога и убедитесь, что цены товаров из категорий sale-category и clearance отображаются со скидкой.
  • Добавьте товары из этих категорий в корзину — цены должны быть пересчитаны.
  • Оформите заказ и проверьте, что цена в заказе совпадает с отображаемой со скидкой.
  • Проверьте товары из других категорий — их цены не должны изменяться.

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

  • Цены не меняются на фронтенде: возможно, тема или кэш плагинов кэшируют цену. Очистите кэш и проверьте работу на дефолтной теме.
  • Скидка применяется несколько раз: убедитесь, что функция custom_category_based_price вызывается только один раз. Избегайте дублирования фильтров.
  • Некорректное округление цен: всегда используйте round($price, 2) для правильного формата цены.
  • Скидка применяется не к тем категориям: проверьте правильность slug категорий и их наличие у товаров.

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

  • Не храните изменённые цены в базе — используйте динамические фильтры, чтобы избежать конфликтов при обновлении товаров.
  • Кешируйте результаты wp_get_post_terms, если на сайте очень много товаров, чтобы снизить нагрузку.
  • При большом количестве категорий и сложных скидках рассмотрите использование плагинов-кешировщиков WooCommerce, чтобы ускорить выдачу страниц.
  • Для управления скидками и акциями более гибко можно использовать плагин Clearfy Pro, который помогает оптимизировать работу магазина и управлять SEO и ценами.

Сравнение вариантов реализации автоматической скидки по категориям

МетодПлюсыМинусыПример
Код на хуках WooCommerceГибкость, бесплатность, контрольТребует навыков PHP, возможно замедление без оптимизацииЭтот пример статьи
Плагины скидок (например, WooCommerce Dynamic Pricing)Удобство, интерфейс, множество настроекПлатные, нагрузка на сайтDynamic Pricing
Ручное изменение ценПростотаТрудозатратно, риск ошибокРедактирование каждого товара
WooCommerce: как настроить авторизацию по email вместо логина
07.05.2026
Как избежать фейковых регистраций в WordPress: проверенные методы и примеры
24.12.2025
Как установить и настроить WPGPT для автоматизации контента в WordPress
12.02.2026
Как создать собственный шорткод в WordPress
18.11.2025
Как добавить изображение в известку WordPress поста
18.02.2026