Как отключить заказы без оплаты в WooCommerce и оставить только оплаченные способы

Ситуация типовая: в магазине есть способы оплаты вроде «Оплата при получении», «Банковский перевод» или просто включённый чек-аут без жёсткой привязки к платёжному шлюзу, а бизнесу нужны только оплаченные заказы. В админке это часто выглядит как «лишние» заказы со статусом pending или on-hold, которые потом вручную фильтруют, отменяют или проверяют отдельно. Если задача не в том, чтобы убрать конкретный платёжный модуль, а именно запретить оформление заказа без оплаты, решение лучше делать на уровне доступных способов оплаты и проверки корзины.

Когда это действительно проблема

Отключать «заказы без оплаты» имеет смысл, если магазин работает по предоплате и нет сценариев самовывоза с оплатой на месте. Иначе вы просто отрежете часть нормальных заказов. Перед правками проверьте, откуда именно появляются неоплаченные заказы:

  • включён способ оплаты, который не проводит платёж сразу;
  • платёжный шлюз возвращает заказ в pending payment из-за ошибки редиректа или webhook;
  • в корзине есть товары, для которых включены особые условия оплаты;
  • кастомный код или плагин меняет доступные методы оплаты на лету.

Диагностика перед изменениями

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

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

Что выбрать: плагин, код или настройка шлюза

Если нужен быстрый результат без разработки, сначала проверьте настройки самого платёжного модуля. Многие шлюзы позволяют ограничить способы оплаты по странам, ролям, сумме заказа или типу доставки. Если этого недостаточно, проще и надёжнее добавить небольшой код в тему или мини-плагин.

Подход Когда подходит Минус
Настройки платёжного шлюза Нужно отключить один конкретный способ оплаты Не решает общую логику магазина
Код через WooCommerce hooks Нужно убрать все неоплачиваемые сценарии или ограничить их по условиям Требует тестирования после обновлений
Плагин для условий оплаты Нужны сложные правила без разработки Дополнительная зависимость и риск конфликтов

Пошаговое решение через код

Ниже пример, который убирает из checkout способы оплаты без мгновенного подтверждения, если в корзине есть только обычные товары. Логику можно адаптировать под свой магазин: оставить только онлайн-эквайринг, а перевод, наложенный платёж и оплату при получении скрыть.

<?php
add_filter( 'woocommerce_available_payment_gateways', 'wpnote_limit_payment_gateways' );
function wpnote_limit_payment_gateways( $gateways ) {
    if ( is_admin() ) {
        return $gateways;
    }

    if ( ! is_checkout() || is_wc_endpoint_url() ) {
        return $gateways;
    }

    // Оставляем только онлайн-оплату.
    $allowed = array( 'stripe', 'yookassa', 'robokassa' );

    foreach ( $gateways as $gateway_id => $gateway ) {
        if ( ! in_array( $gateway_id, $allowed, true ) ) {
            unset( $gateways[ $gateway_id ] );
        }
    }

    return $gateways;
}

Этот вариант полезен, если вы точно знаете список платёжных модулей. Но в реальном магазине часто нужно не просто «разрешить только эти шлюзы», а учитывать состав корзины. Например, для цифровых товаров можно оставить только онлайн-оплату, а для самовывоза — другой набор методов.

Вариант с проверкой корзины

Если в магазине есть смешанные сценарии, удобнее проверять товары в корзине и отключать офлайн-методы только для определённых категорий. Ниже пример: если в корзине есть товар из категории digital, убираем оплату при получении и банковский перевод.

<?php
add_filter( 'woocommerce_available_payment_gateways', 'wpnote_disable_offline_payments_for_digital_goods' );
function wpnote_disable_offline_payments_for_digital_goods( $gateways ) {
    if ( is_admin() || ! WC()->cart ) {
        return $gateways;
    }

    $has_digital = false;

    foreach ( WC()->cart->get_cart() as $cart_item ) {
        $product_id = $cart_item['product_id'];

        if ( has_term( 'digital', 'product_cat', $product_id ) ) {
            $has_digital = true;
            break;
        }
    }

    if ( $has_digital ) {
        unset( $gateways['cod'] );
        unset( $gateways['bacs'] );
    }

    return $gateways;
}

Здесь используются стандартные идентификаторы WooCommerce: cod для оплаты при получении и bacs для банковского перевода. У конкретного шлюза ID может отличаться, поэтому перед внедрением проверьте его в настройках или в коде плагина оплаты.

Если нужно запретить создание заказа без оплаты полностью

Иногда задача жёстче: нельзя даже создать заказ, пока не выбран онлайн-метод оплаты. В этом случае лучше не просто скрывать методы, а валидировать checkout и показывать понятную ошибку пользователю. Так вы не получите «пустые» заказы и не сломаете логику оформления.

<?php
add_action( 'woocommerce_after_checkout_validation', 'wpnote_require_online_payment', 10, 2 );
function wpnote_require_online_payment( $data, $errors ) {
    $chosen = WC()->session ? WC()->session->get( 'chosen_payment_method' ) : '';

    $allowed = array( 'stripe', 'yookassa', 'robokassa' );

    if ( ! in_array( $chosen, $allowed, true ) ) {
        $errors->add( 'payment_method', 'Выберите способ онлайн-оплаты. Оформление без оплаты отключено.' );
    }
}

Этот код не подменяет платёжный шлюз и не создаёт заказ «в обход». Он просто останавливает оформление, если выбран неподходящий метод. Для магазина с предоплатой это обычно самый прозрачный вариант.

Как проверить, что решение сработало

После внедрения не ограничивайтесь одной тестовой оплатой. Проверьте несколько сценариев:

  • корзина с обычным товаром и онлайн-оплатой;
  • корзина с товаром, для которого раньше был доступен cod;
  • оформление заказа в режиме гостя и под авторизованным пользователем;
  • возврат на checkout после ошибки платёжного шлюза;
  • создание заказа на мобильном устройстве, где иногда иначе работает обновление методов оплаты.

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

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

Скрыли метод оплаты, но он всё равно появляется

Чаще всего причина в кэше страницы или в том, что тема/плагин выводит checkout через AJAX и не подхватывает изменение фильтра. Очистите кэш, проверьте страницу без оптимизаторов и убедитесь, что код подключён в активной теме или в отдельном мини-плагине.

После правки checkout начал ругаться на отсутствие способа оплаты

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

Заказы всё равно создаются без оплаты

Проверьте, не стоит ли у платёжного шлюза режим тестирования, и посмотрите логи WooCommerce. Если платёжный модуль создаёт заказ до подтверждения транзакции, это нормальное поведение для многих интеграций. Тогда нужно не запрещать создание заказа, а исправлять callback/webhook и статусы оплаты.

Код сломался после обновления темы

Если вы вставили его в functions.php, он действительно может исчезнуть при смене темы. Для таких задач лучше использовать дочернюю тему или небольшой собственный плагин. Это проще сопровождать и безопаснее для обновлений.

Безопасность и производительность

Фильтр woocommerce_available_payment_gateways вызывается на checkout, поэтому тяжёлую логику туда лучше не добавлять. Не делайте внутри него запросы к внешним API и не перебирайте лишний раз большие массивы. Для сложных правил достаточно проверить корзину, категорию товара или выбранный способ доставки.

Если магазин большой, храните правила в одном месте. Размазанный по теме код быстро становится источником ошибок: один фрагмент скрывает cod, другой снова его возвращает, и отладка превращается в угадайку. Для более сложных сценариев удобнее вынести правила в отдельный мини-плагин или использовать плагин условий оплаты с понятной логикой и журналом изменений.

Если вам нужно не только ограничить способы оплаты, но и убрать лишние элементы на checkout, иногда помогает связка с плагином оптимизации вроде Clearfy Pro: он полезен для чистки лишнего мусора и дублей, но сам по себе не решает бизнес-логику оплат. Здесь всё равно нужен код или настройка платёжного модуля.

WooCommerce: не отображается кнопка «Добавить в корзину» при использовании кастомных шаблонов — как исправить
25.06.2026
Как отключить Gutenberg и вернуть классический редактор в WordPress
04.01.2026
WooCommerce: не работает обновление статуса заказа через REST API — как исправить
07.08.2026
Как создать собственный shortcode в WordPress
06.11.2025
Как установить и настроить WooCommerce на WordPress
14.11.2025