В чем суть задачи: зачем нужна отложенная оплата с подтверждением
В стандартном WooCommerce платеж происходит сразу после оформления заказа. Однако в некоторых случаях требуется, чтобы заказ сначала подтвердил администратор, а покупатель оплатил позже — например, при проверке наличия товара, согласовании скидок или условий доставки.
Реализация отложенной оплаты с подтверждением администратора позволяет контролировать процесс, снижает риск мошенничества и улучшает клиентский сервис.
Диагностика проблемы: почему стандартные методы не подходят
Стандартный WooCommerce не предусматривает отложенный платеж с подтверждением. Плагины с предоплатой или частичной оплатой часто слишком громоздки или не подходят под конкретные бизнес-процессы.
Попытки просто менять статус заказа вручную без автоматизации ведут к ошибкам и неудобствам:
- Покупатель получает письмо с просьбой оплатить заказ без объяснений.
- Отсутствует механизм блокировки оплаты до подтверждения.
- Сложно интегрировать уведомления и логику для администратора.
Пошаговое решение: добавляем отложенную оплату с подтверждением через код
1. Создаем новый статус заказа "Ожидает подтверждения"
Добавим кастомный статус заказа, чтобы отделить неподтвержденные заказы:
add_action('init', 'register_pending_confirmation_order_status');
function register_pending_confirmation_order_status() {
register_post_status('wc-pending-confirmation', array(
'label' => 'Ожидает подтверждения',
'public' => true,
'exclude_from_search' => false,
'show_in_admin_all_list' => true,
'show_in_admin_status_list' => true,
'label_count' => _n_noop('Ожидает подтверждения <span class="count">(%s)</span>', 'Ожидает подтверждения <span class="count">(%s)</span>')
));
}2. Добавляем новый статус в список статусов WooCommerce
add_filter('wc_order_statuses', 'add_pending_confirmation_to_order_statuses');
function add_pending_confirmation_to_order_statuses($order_statuses) {
$new_statuses = array();
foreach ($order_statuses as $key => $status) {
$new_statuses[$key] = $status;
if ('wc-pending' === $key) {
$new_statuses['wc-pending-confirmation'] = 'Ожидает подтверждения';
}
}
return $new_statuses;
}3. Назначаем заказам статус "Ожидает подтверждения" при оформлении
По умолчанию при оформлении заказа статус будет "pending", переназначим его:
add_action('woocommerce_thankyou', 'set_order_status_to_pending_confirmation');
function set_order_status_to_pending_confirmation($order_id) {
if (!$order_id) return;
$order = wc_get_order($order_id);
if ($order && $order->get_status() === 'pending') {
$order->update_status('pending-confirmation', 'Статус изменён на "Ожидает подтверждения" для ручного подтверждения.');
}
}4. Блокируем оплату до подтверждения
В шаблоне оплаты (checkout) надо скрыть способы оплаты или отключить кнопку, если заказ в статусе "pending-confirmation".
Для упрощения добавим фильтр, который отключит оплату для таких заказов на странице "Мои заказы" и в корзине:
add_filter('woocommerce_available_payment_gateways', 'disable_payment_gateways_for_pending_confirmation');
function disable_payment_gateways_for_pending_confirmation($available_gateways) {
if (!is_user_logged_in()) return $available_gateways;
$user_orders = wc_get_orders(array(
'customer' => get_current_user_id(),
'limit' => 1,
'orderby' => 'date',
'order' => 'DESC',
'status' => 'pending-confirmation',
));
if (!empty($user_orders)) {
return array(); // Отключаем все способы оплаты
}
return $available_gateways;
}5. Добавляем уведомления для администратора
Чтобы администратор видел новые заказы с этим статусом, можно добавить уведомление или использовать стандартный список заказов в админке с фильтром:
add_filter('manage_edit-shop_order_columns', 'add_pending_confirmation_column', 20);
function add_pending_confirmation_column($columns) {
$new_columns = array();
foreach ($columns as $key => $column) {
$new_columns[$key] = $column;
if ('order_status' === $key) {
$new_columns['pending_confirmation_count'] = 'Заказы на подтверждении';
}
}
return $new_columns;
}6. Как администратор подтверждает заказ и открывает оплату
Администратор меняет статус заказа вручную на "processing" или "on-hold", после чего покупатель получает стандартное письмо с инструкциями по оплате.
Проверка результата после внедрения
- Оформите заказ от имени тестового пользователя. Статус должен быть "Ожидает подтверждения".
- Проверьте, что на странице "Мои заказы" или в корзине оплата заблокирована (кнопка "Оплатить" отсутствует).
- В админке проверьте, что заказ появился со статусом "Ожидает подтверждения".
- Измените статус заказа на "processing" и убедитесь, что покупатель получил уведомление и может оплатить заказ.
Частые ошибки и как их исправить
- Статус не отображается в списке заказов: Проверьте, что функции на регистрации статуса и добавления в список статусов подключены к хукам
initиwc_order_statuses. - Оплата не блокируется: Убедитесь, что фильтр
woocommerce_available_payment_gatewaysкорректно проверяет статус последнего заказа пользователя. - Покупатель не получает уведомление после смены статуса: Проверьте, что в настройках WooCommerce включены уведомления для нужных статусов, или добавьте кастомные email-уведомления.
Практические советы по безопасности и производительности
- Используйте nonce и capability-проверки при добавлении кастомных действий администратора для смены статуса.
- Оптимизируйте запросы
wc_get_ordersс ограничением по дате и количеству, чтобы не нагружать базу. - Включите логирование действий со статусами для аудита и быстрого выявления проблем.
Сравнение способов реализации отложенной оплаты
| Способ | Преимущества | Недостатки |
|---|---|---|
| Плагин предоплаты | Готовое решение, поддержка | Нагрузка, платные, могут быть избыточными |
| Кастомный статус + код (как выше) | Легкий, точечный, гибкий | Нужно писать и поддерживать код |
| Использование купонов и скидок для «заморозки» заказа | Простота настройки без кода | Неочевидно для пользователя, сложная логика |