Проблема: автоматическое изменение остатков товаров в WooCommerce по API
Автоматическое обновление остатков товаров по API в WooCommerce удобно для синхронизации с внешними системами, например, с ERP или складским учётом. Однако в некоторых случаях это приводит к нежелательным ситуациям: остатки сбрасываются некорректно, данные дублируются, или сторонние сервисы некорректно передают информацию. В результате на сайте отображается неверный запас, что ведёт к ошибкам в заказах и недовольству клиентов.
Диагностика проблемы
- Проверьте, какие внешние сервисы подключены для обновления запасов через WooCommerce REST API или сторонние плагины.
- Отследите логи запросов к API, чтобы понять, когда и с какими данными обновляются остатки.
- Определите, влияет ли автоматическое обновление непосредственно на записи
stock_quantityу товаров WooCommerce. - Проверьте, не запускаются ли сторонние крон-задачи или хуки, которые могут обновлять остатки без контроля.
Пошаговое решение: отключение автоматического обновления запасов по API
WooCommerce не имеет встроенной функции «отключить обновление остатков по API», поскольку API — это интерфейс для программного взаимодействия. Чтобы запретить автоматическое изменение запасов через API, необходимо перехватить соответствующие запросы и предотвратить обновление поля stock_quantity. Это можно сделать через фильтры WooCommerce.
1. Запрет на обновление запаса через REST API
Добавьте следующий код в файл functions.php вашей темы или в кастомный плагин:
add_filter('woocommerce_rest_pre_insert_product_object', function($product, $request) {
if (isset($request['stock_quantity'])) {
// Удаляем параметр, чтобы не обновлять запас
unset($request['stock_quantity']);
}
return $product;
}, 10, 2);Этот фильтр предотвращает обновление поля stock_quantity при обработке REST API запроса на обновление товара.
2. Блокировка массового обновления остатков через WP-CLI или другие скрипты
Если обновление происходит не только через REST API, но и через скрипты, можно добавить защиту при сохранении товара, чтобы не менять запас:
add_action('woocommerce_before_product_object_save', function($product) {
// Получаем старое значение запаса
$old_stock = $product->get_meta('_old_stock_quantity');
if ($old_stock !== '') {
$product->set_stock_quantity($old_stock);
}
});
add_action('woocommerce_after_product_object_save', function($product) {
// Сохраняем текущий запас, чтобы потом не менять его
$product->update_meta_data('_old_stock_quantity', $product->get_stock_quantity());
});Этот код сохраняет текущий запас в метаполе и восстанавливает его при попытке изменить.
Проверка результата после внедрения
- Отправьте запрос обновления товара через REST API с параметром
stock_quantityи убедитесь, что запас не изменился. - Попробуйте обновить запас вручную в админке WooCommerce — изменение должно работать, если нужно.
- Проверьте логи сервера на отсутствие ошибок, связанных с REST API.
- Если у вас есть сторонние интеграции, протестируйте их работу и убедитесь, что запасы не меняются автоматически.
Частые ошибки и как исправить
- Код не работает, запасы всё равно обновляются: проверьте, не перезаписывает ли другие хуки или плагины поле
stock_quantity. Используйте приоритет фильтра выше (например, 20) или отладьте последовательность вызовов. - Нарушается работа сторонних функций, которые должны обновлять запасы: в этом случае стоит реализовать более тонкую логику с проверкой источника запроса (например, IP, user-agent, авторизация), чтобы не блокировать легитимные обновления.
- Ошибка синхронизации данных: если данные приходят из нескольких источников, рассмотрите использование очередей обновлений или отдельного сервиса для агрегации запасов.
Практические советы по безопасности и производительности
- Ограничьте доступ к REST API по IP или методам аутентификации, чтобы исключить несанкционированные обновления.
- Ведите логирование запросов на обновление запасов для быстрого обнаружения проблем.
- При большом количестве товаров и частых обновлениях используйте кеширование и отложенную обработку (cron) для снижения нагрузки на базу.
- Тестируйте изменения на staging-среде, чтобы избежать сбоев в рабочем магазине.
Сравнение вариантов решения
| Метод | Описание | Плюсы | Минусы |
|---|---|---|---|
Фильтр woocommerce_rest_pre_insert_product_object | Блокирует обновление stock_quantity через REST API | Простая реализация, быстрое решение | Не блокирует обновления из других источников |
| Хуки сохранения товара | Восстанавливает старое значение запаса при сохранении | Работает для любых обновлений, включая WP-CLI | Сложнее в поддержке, может конфликтовать с легитимными обновлениями |
| Ограничение доступа к API | Ограничивает кто может делать запросы на обновление | Повышает безопасность | Требует настройки сервера и аутентификации |