Диагностика проблемы: зачем удалять заказы после архивирования
В стандартном WooCommerce архивирование заказа лишь меняет его статус, но не удаляет данные из базы. Это может привести к росту размера базы и замедлению работы сайта, особенно при большом количестве заказов. Автоматическое удаление заказов после архивирования позволяет поддерживать базу данных в оптимальном состоянии без ручного вмешательства.
Пошаговое решение: автоматическое удаление заказов с подтверждением
1. Добавление пользовательского статуса "архивирован" (если его нет)
Если вы используете стандартный статус "архивирован" или кастомный, убедитесь, что он зарегистрирован в WooCommerce.
add_filter('wc_order_statuses', 'register_archived_order_status');
function register_archived_order_status($order_statuses) {
$order_statuses['wc-archived'] = _x('Archived', 'Order status', 'woocommerce');
return $order_statuses;
}
add_action('init', 'add_archived_order_status');
function add_archived_order_status() {
register_post_status('wc-archived', array(
'label' => 'Archived',
'public' => false,
'exclude_from_search' => false,
'show_in_admin_all_list' => true,
'show_in_admin_status_list' => true,
'label_count' => _n_noop('Archived <span class="count">(%s)</span>', 'Archived <span class="count">(%s)</span>'),
));
}2. Автоматическое удаление заказа после смены статуса на архивированный с подтверждением
Добавим проверку через AJAX, чтобы пользователь подтвердил удаление, и только затем заказ удалялся.
add_action('woocommerce_order_status_changed', 'auto_delete_archived_order', 10, 4);
function auto_delete_archived_order($order_id, $old_status, $new_status, $order) {
if ($new_status === 'archived') {
// Отправим администратору письмо с просьбой подтвердить удаление или создадим интерфейс на фронтенде
// Здесь простой пример: заказ помечается для удаления, а фактическое удаление происходит после подтверждения
update_post_meta($order_id, '_pending_deletion', 'yes');
}
}
// AJAX обработчик подтверждения удаления
add_action('wp_ajax_confirm_delete_order', 'confirm_delete_order_callback');
function confirm_delete_order_callback() {
if (!current_user_can('manage_woocommerce')) {
wp_send_json_error('Нет прав для удаления заказов');
}
$order_id = isset($_POST['order_id']) ? intval($_POST['order_id']) : 0;
if (!$order_id) {
wp_send_json_error('Неверный ID заказа');
}
$pending = get_post_meta($order_id, '_pending_deletion', true);
if ($pending !== 'yes') {
wp_send_json_error('Удаление не запланировано');
}
wp_delete_post($order_id, true);
wp_send_json_success('Заказ удалён');
}3. Добавление кнопки подтверждения удаления в админ-панели
Для удобства администратора можно добавить кнопку удаления в список заказов или на страницу заказа, которая отправляет AJAX-запрос на удаление.
add_action('woocommerce_admin_order_actions_end', 'add_confirm_delete_button');
function add_confirm_delete_button($order) {
$pending = get_post_meta($order->get_id(), '_pending_deletion', true);
if ($pending === 'yes') {
$nonce = wp_create_nonce('confirm_delete_order_nonce');
echo '<button class="button confirm-delete-order" data-order-id="' . $order->get_id() . '" data-nonce="' . $nonce . '">Подтвердить удаление</button>';
}
}
// JS для отправки AJAX (регистрируется отдельно в админке)
/*
jQuery(document).on('click', '.confirm-delete-order', function() {
var button = jQuery(this);
var orderId = button.data('order-id');
var nonce = button.data('nonce');
if (!confirm('Вы уверены, что хотите удалить заказ #' + orderId + '?')) return;
jQuery.post(ajaxurl, {
action: 'confirm_delete_order',
order_id: orderId,
_ajax_nonce: nonce
}, function(response) {
if (response.success) {
alert('Заказ удалён');
location.reload();
} else {
alert('Ошибка: ' + response.data);
}
});
});
*/Проверка результата после внедрения
- Создайте тестовый заказ и переведите его в статус "archived".
- Проверьте, появится ли кнопка подтверждения удаления в админке на странице заказа или в списке заказов.
- Нажмите кнопку и подтвердите удаление — заказ должен полностью удалиться из базы.
- Проверьте таблицу
wp_postsна наличие заказа (должен отсутствовать), а такжеwp_postmetaдля связанных метаданных.
Частые ошибки и как их исправить
- Отсутствие регистрации статуса "archived" — удаление не срабатывает, так как событие смены статуса не ловится. Исправляется добавлением кода регистрации статуса.
- Отсутствие прав у пользователя — AJAX-запрос отклоняется. Проверьте capability
manage_woocommerceили настройте роли. - Кнопка подтверждения не появляется — ошибка в хуке добавления кнопки или проблема с проверкой мета-поля. Проверьте наличие мета-ключа
_pending_deletion. - Удаление не происходит — убедитесь, что
wp_delete_postвызывается с параметромtrueдля полного удаления, а не в корзину.
Практические советы по безопасности и производительности
- Всегда добавляйте проверку nonce и capability для AJAX-запросов, чтобы исключить несанкционированное удаление.
- В крупных магазинах с большим количеством заказов используйте пакетную обработку удалений через WP-CLI или CRON, чтобы не нагружать сайт.
- Регулярно делайте резервные копии базы данных перед массовым удалением данных.
- Для мониторинга состояния базы используйте плагины оптимизации типа Clearfy Pro (https://wpshop.ru/plugins/clearfy?utm_source=wpsolution.ru&utm_medium=article&utm_campaign=woocommerce-avtomaticheskoe-udaleniye-zakazov-posle-arkhivirovaniya-s-podtverzhdeniem), которые помогут отслеживать рост таблиц и удалять неиспользуемые данные.
Сравнение вариантов удаления заказов после архивирования
| Способ | Описание | Плюсы | Минусы |
|---|---|---|---|
| Удаление через хук без подтверждения | Прямое удаление при смене статуса | Автоматизация, простота | Риск случайного удаления, нет контроля |
| Удаление с подтверждением через AJAX | Удаление после явного подтверждения администратора | Безопасно, контроль пользователя | Требует доработки интерфейса |
| Ручное удаление | Администратор удаляет заказы вручную | Полный контроль | Трудозатратно, риск забыть удалить |