Диагностика проблемы: как определить неактивные товары в WooCommerce
Неактивные товары — это те, которые не продавались или не обновлялись длительное время и не должны отображаться в каталоге, чтобы не загромождать магазин и не вводить покупателей в заблуждение. Проблема в том, что WooCommerce не имеет встроенных инструментов для автоматического отключения таких товаров. Поэтому часто наблюдается ситуация, когда устаревшие или неактуальные товары продолжают висеть в магазине.
Для диагностики неактивных товаров можно использовать критерии:
- Дата последней продажи (заказа с товаром)
- Дата последнего обновления товара (post_modified)
- Количество просмотров или добавлений в корзину (если ведется статистика)
В админке WooCommerce стандартных фильтров по этим параметрам нет, поэтому необходимо реализовать кастомное решение.
Пошаговое решение: автоматическое отключение неактивных товаров с помощью кода
1. Определяем неактивные товары
Напишем функцию, которая будет искать товары без продаж за последние 180 дней и отключать их, меняя статус на «черновик» (draft).
function disable_inactive_products() {
global $wpdb;
$days_inactive = 180; // Период неактивности в днях
$date_threshold = date('Y-m-d H:i:s', strtotime("-" . $days_inactive . " days"));
// Получаем ID товаров, у которых не было заказов после $date_threshold
$product_ids = $wpdb->get_col(
$wpdb->prepare(
"SELECT p.ID FROM {$wpdb->posts} p
LEFT JOIN {$wpdb->prefix}woocommerce_order_items oi ON oi.order_item_id IN
(SELECT order_item_id FROM {$wpdb->prefix}woocommerce_order_itemmeta WHERE meta_key = '_product_id' AND meta_value = p.ID)
LEFT JOIN {$wpdb->posts} o ON o.ID = oi.order_id AND o.post_type = 'shop_order' AND o.post_status IN ('wc-completed','wc-processing')
WHERE p.post_type = 'product' AND p.post_status = 'publish'
GROUP BY p.ID HAVING MAX(o.post_date) < %s OR MAX(o.post_date) IS NULL",
$date_threshold
)
);
if (!empty($product_ids)) {
foreach ($product_ids as $product_id) {
wp_update_post([
'ID' => $product_id,
'post_status' => 'draft'
]);
}
}
}2. Запускаем функцию по расписанию через WP-Cron
Для автоматизации создадим cron-задачу, которая будет запускать эту функцию раз в сутки.
function schedule_disable_inactive_products() {
if (!wp_next_scheduled('disable_inactive_products_daily')) {
wp_schedule_event(time(), 'daily', 'disable_inactive_products_daily');
}
}
add_action('wp', 'schedule_disable_inactive_products');
add_action('disable_inactive_products_daily', 'disable_inactive_products');3. Очистка cron при деактивации темы или плагина
function clear_disable_inactive_products_schedule() {
$timestamp = wp_next_scheduled('disable_inactive_products_daily');
if ($timestamp) {
wp_unschedule_event($timestamp, 'disable_inactive_products_daily');
}
}
register_deactivation_hook(__FILE__, 'clear_disable_inactive_products_schedule');Проверка результата после внедрения
- Запустите функцию вручную:
disable_inactive_products();в файле functions.php или через WP-CLI. - Проверьте, что товары без заказов за последние 180 дней получили статус «черновик» в админке WooCommerce.
- Наблюдайте за автоматическим запуском cron-задачи через плагин WP Crontrol или вызовом
wp cron event run disable_inactive_products_daily. - Убедитесь, что отключённые товары не отображаются в каталоге и не доступны покупателям.
Частые ошибки и как их исправить
- Ошибка: Нет изменений после запуска функции.
Причина: Неправильный формат даты или отсутствуют заказы в нужном статусе.
Решение: Проверьте корректность даты и статусов заказов (лучше использовать «wc-completed» и «wc-processing»). - Ошибка: Cron-задача не запускается.
Причина: WP-Cron отключён или отсутствует посещение сайта.
Решение: Используйте системный cron для реального планировщика или вручную тестируйте через WP-CLI. - Ошибка: Отключаются товары, которые недавно обновлялись.
Причина: Функция не учитывает дату обновления товара.
Решение: Можно расширить логику, добавив проверкуpost_modified.
Практические советы по безопасности и производительности
- Запрос SQL достаточно тяжелый — убедитесь, что база данных оптимизирована. Используйте индексы по
post_type,post_statusи таблицам WooCommerce. - Ограничьте период неактивности, чтобы не отключать слишком ранние товары, например, не менее 90 дней.
- Добавьте логирование отключенных товаров для аудита и возможности восстановления.
- Не запускайте cron слишком часто — достаточно раза в сутки.
Сравнение вариантов реализации автоматического отключения неактивных товаров
| Метод | Преимущества | Недостатки | Рекомендации |
|---|---|---|---|
| Кастомный код с WP-Cron | Полный контроль, без лишних плагинов, гибкость | Требует навыков разработки, нагрузка на БД при большом каталоге | Использовать при большом количестве товаров и специфичных критериях |
| Плагины для управления товарами | Простота установки, готовые интерфейсы | Могут быть избыточными, не всегда гибкие, нагрузка | Подходит для малого и среднего магазина |
| Ручное отключение товаров | Простой подход, без кода | Трудозатратно, неудобно при большом количестве товаров | Подходит для небольших магазинов с ограниченным ассортиментом |