WooCommerce: автоматическое возвратное действие при отклонённом платеже

Диагностика проблемы: почему заказ остаётся в статусе "Ошибка платежа" и не обновляется

В WooCommerce иногда возникает ситуация, когда платеж отклонён, но статус заказа остаётся прежним, и не происходит автоматического возврата средств или уведомления клиента. Это создаёт путаницу и требует ручного вмешательства. Причины могут быть в неправильной обработке статусов платежей, отсутствии нужных хуков или конфликте плагинов.

Как понять, что проблема именно в этом

  • Проверить статус заказа в админке — он остаётся «Ошибка платежа» или «On hold» после неудачной оплаты.
  • Посмотреть логи платежного шлюза — есть ли подтверждение отклонения.
  • Отсутствие автоматических писем клиенту о возврате или ошибке.
  • Отсутствие автоматической смены статуса или возврата средств.

Пошаговое решение: автоматическое обновление статуса заказа и возврат средств при ошибках оплаты

Для автоматизации задачи можно использовать хук woocommerce_order_status_failed, который срабатывает при переходе заказа в статус failed. В этом хуке вызовем функцию для возврата средств и уведомления клиента.

Пример кода, который нужно добавить в файл functions.php вашей темы или в кастомный плагин:

add_action('woocommerce_order_status_failed', 'auto_refund_on_failed_payment');
function auto_refund_on_failed_payment($order_id) {
    if (!$order_id) return;
    $order = wc_get_order($order_id);
    
    // Проверяем, есть ли уже возврат
    $refunds = $order->get_refunds();
    if (!empty($refunds)) {
        return; // Возврат уже был выполнен
    }

    // Создаём возврат на всю сумму заказа
    $refund = wc_create_refund(array(
        'amount' => $order->get_total(),
        'reason' => 'Автоматический возврат при ошибке платежа',
        'order_id' => $order_id,
        'refund_payment' => true, // попытка вернуть деньги через шлюз
    ));

    if (is_wp_error($refund)) {
        error_log('Ошибка при автоматическом возврате для заказа ' . $order_id . ': ' . $refund->get_error_message());
    } else {
        // Обновляем статус заказа на refunded
        $order->update_status('refunded', 'Автоматический возврат выполнен.');
        // Отправляем уведомление клиенту
        WC()->mailer()->customer_refunded_order($order);
    }
}

Обратите внимание, что wc_create_refund инициирует возврат через платёжный шлюз, если он поддерживает возвраты через API. Иначе возврат будет только в админке.

Настройка вебхуков платежного шлюза

Для корректной работы возвратов убедитесь, что у вашего платёжного шлюза настроены вебхуки (webhooks), которые уведомляют WooCommerce о смене статуса оплаты. Иначе WooCommerce не узнает об ошибке и статус не поменяется.

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

  • Создайте тестовый заказ с платёжным методом, который можно отклонить (например, тестовый режим в Stripe или PayPal).
  • Имитируйте ошибку платежа.
  • Проверьте, что статус заказа изменился на refunded автоматически.
  • Проверьте наличие возврата в деталях заказа.
  • Удостоверьтесь, что клиент получил письмо об отмене и возврате.
  • Просмотрите логи ошибок WordPress на наличие сообщений из функции возврата.

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

  • Возврат не создаётся, ошибка "Refund failed": возможно, платёжный шлюз не поддерживает автоматические возвраты через API или нет доступа. Проверьте настройки API и права аккаунта.
  • Хук не срабатывает: убедитесь, что статус заказа действительно меняется на failed. Иногда платёжные шлюзы используют свои статусы. Можно добавить логирование или временно заменить woocommerce_order_status_failed на woocommerce_order_status_changed для отладки.
  • Письмо клиенту не отправляется: проверьте настройки почты WooCommerce и тестируйте отправку на другие шаблоны.
  • Возврат создаётся несколько раз: в коде уже предусмотрена проверка, но если она не срабатывает, добавьте более строгие проверки или флаги.

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

  • Проверяйте права доступа к API платёжного шлюза, чтобы избежать злоупотреблений.
  • Логируйте ошибки возврата в отдельный файл или через системные логи, чтобы вовремя реагировать.
  • Не делайте возврат автоматически, если сумма заказа нулевая или уже был возврат — это может привести к ошибкам.
  • Используйте отложенные задачи через WP-Cron для повторных попыток возврата, если первая не удалась.

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

СпособПлюсыМинусыПример использования
Ручное обновление статуса и возврата Полный контроль, простота Требует ручной работы, ошибки Админка WooCommerce
Хук woocommerce_order_status_failed с автозапуском возврата Автоматизация, меньше ручной работы Зависимость от корректной работы шлюза Пример кода из статьи
Плагин для автоматизации возвратов (например, Refund Manager) Готовое решение, поддержка Дополнительные расходы, может конфликтовать Плагины из репозитория
Как использовать REST API для создания кастомных эндпоинтов в WordPress
10.12.2025
Как установить ограничение доступа к записям WordPress по ролям пользователя
29.12.2025
WooCommerce: автоматическое изменение цены товара при расширенном дисконте
06.05.2026
Как использовать AJAX для пагинации в WordPress с примерами кода
24.03.2026
Как добавить свои свойства в метаданные постов WordPress
11.11.2025