Диагностика проблемы: зачем удалять товары без заказов
Магазины WooCommerce часто накапливают сотни и тысячи товаров, часть из которых так и не была куплена. Это может создавать нагрузку на базу данных, усложнять навигацию и снижать производительность. Важно уметь автоматически удалять такие товары, чтобы поддерживать чистоту каталога и облегчить администрирование.
Как определить товары без заказов в WooCommerce
Товар считается без заказов, если по нему не было оформлено ни одного заказа. Это можно проверить через связи таблиц базы данных или через WP_Query с учетом метаданных заказов.
Пример SQL-запроса для выявления товаров без заказов
SELECT p.ID, p.post_title
FROM wp_posts p
WHERE p.post_type = 'product'
AND p.post_status = 'publish'
AND NOT EXISTS (
SELECT 1 FROM wp_woocommerce_order_items oi
JOIN wp_woocommerce_order_itemmeta oim ON oi.order_item_id = oim.order_item_id
JOIN wp_posts o ON o.ID = oi.order_id
WHERE o.post_type = 'shop_order'
AND o.post_status IN ('wc-completed', 'wc-processing')
AND oim.meta_key = '_product_id'
AND oim.meta_value = p.ID
);
Этот запрос выбирает товары, которые не связаны с заказами в статусах «завершен» и «обрабатывается».
Пошаговое решение: автоматическое удаление товаров без заказов через WP-CLI
Используем WP-CLI — удобный инструмент для управления WordPress из консоли.
- Создаем PHP-скрипт для поиска и удаления товаров без заказов.
- Запускаем скрипт через WP-CLI.
Пример скрипта delete-unused-products.php
<?php
// Загружаем WordPress
require_once dirname(__FILE__) . '/wp-load.php';
// Получаем ID товаров без заказов
function get_unused_products() {
global $wpdb;
$query = "SELECT p.ID FROM {$wpdb->posts} p
WHERE p.post_type = 'product'
AND p.post_status = 'publish'
AND NOT EXISTS (
SELECT 1 FROM {$wpdb->prefix}woocommerce_order_items oi
JOIN {$wpdb->prefix}woocommerce_order_itemmeta oim ON oi.order_item_id = oim.order_item_id
JOIN {$wpdb->posts} o ON o.ID = oi.order_id
WHERE o.post_type = 'shop_order'
AND o.post_status IN ('wc-completed', 'wc-processing')
AND oim.meta_key = '_product_id'
AND oim.meta_value = p.ID
)";
return $wpdb->get_col($query);
}
$unused_products = get_unused_products();
if (empty($unused_products)) {
echo "Нет товаров без заказов.\n";
exit;
}
foreach ($unused_products as $product_id) {
wp_delete_post($product_id, true); // true - удаление без возможности восстановления (без корзины)
echo "Удалён товар ID: $product_id\n";
}
Запуск из терминала:
wp eval-file delete-unused-products.php
Проверка результата после внедрения
- Запустите SQL-запрос из раздела диагностики до и после удаления. Количество товаров без заказов должно уменьшиться.
- Проверьте админку WooCommerce — товары, которые не имели заказов, должны отсутствовать.
- Проверьте логи WP-CLI на предмет ошибок при удалении.
Частые ошибки и как их исправить
- Удаление не всех товаров без заказов: проверьте, что заказы имеют статусы именно
wc-completedилиwc-processing. Возможно, в вашем магазине используются другие статусы для подтвержденных заказов. - Ошибка при подключении к базе данных: убедитесь, что скрипт запускается из корня WordPress, и путь к
wp-load.phpкорректен. - Товары не удаляются, появляются ошибки прав: проверьте разрешения пользователя в WordPress и права на файлы.
- Долгое выполнение скрипта на больших каталогах: разделите удаление на части, например, по 100 товаров за раз, добавьте паузы.
Практические советы по безопасности и производительности
- Перед массовым удалением сделайте полный бэкап базы данных.
- Для больших магазинов запускайте скрипт в ночное время с низкой нагрузкой.
- Вместо полного удаления можно сначала перемещать товары в черновики (
wp_update_post(['ID' => $id, 'post_status' => 'draft'])) для проверки. - Регулярно оптимизируйте базу данных после удаления (
wp db optimizeчерез WP-CLI или SQL-командойOPTIMIZE TABLE). - Для автоматизации запуска используйте cron-задачи с WP-CLI.
Сравнение вариантов удаления товаров без заказов
| Метод | Плюсы | Минусы |
|---|---|---|
| WP-CLI скрипт | Полный контроль, быстро, без плагинов | Требуется доступ к серверу, знание CLI |
| Плагины для очистки каталога | Простой интерфейс, дополнительные функции | Нагрузка на сайт, возможные конфликты, лицензии |
| Ручное удаление через админку | Простота, нет рисков автоматизации | Трудоемко, не подходит для больших магазинов |