WooCommerce: автоматическое отключение способов оплаты при неподтверждённых заказах без плагинов

Проблема: почему важно отключать способы оплаты при неподтверждённых заказах

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

Диагностика проблемы

Чтобы понять, как отключить способы оплаты для неподтверждённых заказов, нужно определить, как WooCommerce обрабатывает статусы заказов и когда показываются методы оплаты.

  • Проверьте, какие статусы заказов считаются неподтверждёнными (чаще всего это pending или on-hold).
  • Проверьте, не влияет ли на это активность сторонних плагинов, которые могут менять логику отображения способов оплаты.
  • Убедитесь, что в настройках WooCommerce корректно настроены статусы заказов и доступные способы оплаты.

Пошаговое решение: как отключить способы оплаты программно

Реализуем фильтр, который будет проверять наличие неподтверждённых заказов у текущего пользователя и при их наличии отключать способы оплаты.

1. Определяем неподтверждённые заказы пользователя

function has_unconfirmed_orders($user_id) {
    if (!$user_id) return false;
    $args = array(
        'customer_id' => $user_id,
        'status'      => array('pending', 'on-hold'),
        'limit'       => 1,
        'return'      => 'ids'
    );
    $orders = wc_get_orders($args);
    return !empty($orders);
}

2. Фильтруем способы оплаты

add_filter('woocommerce_available_payment_gateways', 'disable_payment_methods_for_unconfirmed_orders');
function disable_payment_methods_for_unconfirmed_orders($available_gateways) {
    if (is_admin()) return $available_gateways; // Не трогаем админку

    $user_id = get_current_user_id();
    if (has_unconfirmed_orders($user_id)) {
        // Отключаем все способы оплаты
        $available_gateways = array();
    }
    return $available_gateways;
}

Если нужно отключать не все способы, а только определённые, замените очистку массива на удаление конкретных ключей, например:

unset($available_gateways['cod']); // Отключить оплату при получении
unset($available_gateways['bacs']); // Отключить банковский перевод

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

  • Залогиньтесь под пользователем с неподтверждённым заказом и перейдите на страницу оформления заказа. Способы оплаты должны отсутствовать.
  • Залогиньтесь под пользователем без неподтверждённых заказов — способы оплаты должны отображаться.
  • Проверьте работу на разных устройствах и браузерах, чтобы исключить кэширование.

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

  • Все способы оплаты отключены у всех пользователей. Проверьте корректность функции has_unconfirmed_orders и передаваемый ID пользователя.
  • Способы оплаты не отключаются. Убедитесь, что фильтр добавлен в functions.php или в кастомный плагин. Проверьте, нет ли конфликтов с другими плагинами, изменяющими способы оплаты.
  • Кэширование мешает проверить изменения. Очистите кеш сайта, браузера и если используете кеширующие плагины (например, WP Rocket) — сбросьте их кеш.

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

  • При выборке заказов используйте максимально узкие запросы (например, limit = 1), чтобы не создавать нагрузку.
  • Не отключайте все способы оплаты, если часть из них нужна для определённых сценариев (например, оплата по факту).
  • Для большого количества пользователей и заказов стоит кэшировать результат проверки в user meta с установкой времени жизни (например, 10 минут).
  • Следите, чтобы код выполнялся только на фронтенде — добавляйте проверку !is_admin().

Сравнение вариантов реализации

МетодПлюсыМинусыСложность
Чистый код через фильтр woocommerce_available_payment_gatewaysЛегко кастомизировать, не требует плагинов, полный контрольТребует навыков PHP, нужно тестировать совместимостьСредняя
Плагины для управления способами оплаты (например, Conditional WooCommerce Payments)Простая настройка через интерфейс, быстрая реализацияДополнительная нагрузка на сайт, возможные конфликтыНизкая
Использование кастомных плагинов с WP-Cron для очистки неподтверждённых заказовАвтоматизация очистки, уменьшение нагрузки на оплатуСложность реализации, требует поддержки cronВысокая