Типичный сценарий: заказ в WooCommerce уже оплачен, менеджер меняет статус на processing или completed, а в CRM это событие не доходит. В итоге в CRM висит старый статус, у отдела продаж нет актуальной карточки, а ручная сверка занимает время. Если интеграция нужна только на уровне статусов, вебхук из WordPress обычно проще и надежнее, чем тащить полноценный коннектор.
Когда вебхук лучше плагина
Если CRM умеет принимать HTTP-запросы, можно отправлять туда только нужные поля: номер заказа, статус, сумму, email клиента и дату изменения. Это удобно, когда:
- нужно передавать только смену статуса, а не весь заказ;
- CRM принимает простой
POSTилиPUTна свой endpoint; - важно контролировать формат данных и повторные отправки;
- не хочется зависеть от тяжелого интеграционного плагина.
Если же CRM требует OAuth, сложную очередь синхронизации или двусторонний обмен, кодом на одном хукe задачу лучше не закрывать. В таком случае вебхук можно оставить как часть общей схемы, а не как единственный механизм.
Сравнение подходов
| Подход | Плюсы | Минусы |
|---|---|---|
| Код через хук WooCommerce | Минимум зависимостей, полный контроль над payload | Нужно поддерживать код и обработку ошибок |
| Плагин интеграции | Быстрый старт, иногда есть логирование | Может быть избыточным, сложнее отладка |
| Ручной экспорт | Подходит для разовых выгрузок | Не решает задачу синхронизации статусов |
Диагностика проблемы: что проверить до внедрения
Перед тем как писать код, проверьте саму точку интеграции. Ошибка часто не в WooCommerce, а в стороне CRM или в неверном статусе заказа.
- CRM действительно принимает входящие запросы по HTTPS.
- Есть документация по endpoint: метод, заголовки, формат JSON, авторизация.
- В WooCommerce статус меняется вручную или автоматически тем же способом, который нужно отслеживать.
- Сервер сайта умеет делать исходящие запросы через
wp_remote_post(). - На хостинге не блокируются запросы к внешним доменам через firewall или ограничения PHP.
Если запросы уходят, но CRM их не видит, сначала смотрите ответ сервера и логи. Если запросы не уходят вообще, проблема может быть в SSL, DNS, таймауте или запрете исходящих соединений.
Пошаговое решение: отправка статуса заказа в CRM
Ниже пример для functions.php дочерней темы или, что лучше, для небольшого собственного плагина. Код срабатывает при смене статуса заказа и отправляет данные во внешний endpoint.
add_action( 'woocommerce_order_status_changed', 'wpone_send_order_status_to_crm', 10, 4 );
function wpone_send_order_status_to_crm( $order_id, $old_status, $new_status, $order ) {
if ( ! $order instanceof WC_Order ) {
$order = wc_get_order( $order_id );
}
if ( ! $order ) {
return;
}
// Отправляем только нужные статусы, чтобы не спамить CRM.
$allowed_statuses = array( 'processing', 'completed', 'cancelled', 'refunded' );
if ( ! in_array( $new_status, $allowed_statuses, true ) ) {
return;
}
$endpoint = 'https://crm.example.com/api/order-status';
$secret = 'replace-with-real-secret';
$payload = array(
'order_id' => $order->get_id(),
'order_number' => $order->get_order_number(),
'old_status' => $old_status,
'new_status' => $new_status,
'total' => $order->get_total(),
'currency' => $order->get_currency(),
'email' => $order->get_billing_email(),
'phone' => $order->get_billing_phone(),
'updated_at' => current_time( 'mysql' ),
);
$response = wp_remote_post( $endpoint, array(
'timeout' => 15,
'headers' => array(
'Content-Type' => 'application/json; charset=utf-8',
'X-Webhook-Key' => $secret,
),
'body' => wp_json_encode( $payload ),
) );
if ( is_wp_error( $response ) ) {
error_log( 'CRM webhook error for order ' . $order_id . ': ' . $response->get_error_message() );
return;
}
$code = wp_remote_retrieve_response_code( $response );
if ( $code < 200 || $code >= 300 ) {
error_log( 'CRM webhook bad response for order ' . $order_id . ': HTTP ' . $code );
}
}Что здесь важно:
- мы ограничили список статусов, чтобы не отправлять лишние события;
- данные сериализуются в JSON через
wp_json_encode(); - используется
wp_remote_post(), а не прямой cURL, чтобы код был совместим с WordPress; - ошибки пишутся в лог, иначе отладка превращается в угадывание.
Если CRM требует подпись запроса
Некоторые системы проверяют HMAC-подпись. Тогда можно добавить отдельный заголовок. Пример ниже не привязан к конкретной CRM, но сам принцип рабочий.
$body = wp_json_encode( $payload );
$signature = hash_hmac( 'sha256', $body, 'replace-with-real-secret' );
$response = wp_remote_post( $endpoint, array(
'timeout' => 15,
'headers' => array(
'Content-Type' => 'application/json; charset=utf-8',
'X-Webhook-Sign' => $signature,
),
'body' => $body,
) );Как не отправлять один и тот же заказ дважды
Повторная отправка — частая проблема, особенно если менеджер несколько раз меняет статус туда-сюда. Если CRM не умеет дедупликацию по order_id и new_status, лучше хранить отметку об успешной синхронизации в мета-данных заказа.
add_action( 'woocommerce_order_status_changed', 'wpone_send_order_status_to_crm_once', 10, 4 );
function wpone_send_order_status_to_crm_once( $order_id, $old_status, $new_status, $order ) {
$meta_key = '_wpone_last_crm_status_sent';
$last_sent = get_post_meta( $order_id, $meta_key, true );
if ( $last_sent === $new_status ) {
return;
}
// Здесь вызывайте вашу функцию отправки.
$sent = true;
if ( $sent ) {
update_post_meta( $order_id, $meta_key, $new_status );
}
}Такой подход не заменяет нормальную обработку ошибок, но убирает случайные дубли при повторном сохранении заказа.
Проверка результата после внедрения
После добавления кода не ограничивайтесь визуальной проверкой в админке. Нужно убедиться, что запрос реально дошел и CRM приняла его без ошибок.
- Измените статус тестового заказа на один из отслеживаемых.
- Проверьте
wp-content/debug.logили системный лог сервера на наличие ошибокwp_remote_post(). - Посмотрите журнал входящих запросов в CRM, если он есть.
- Сверьте, что в payload пришли правильные поля: номер заказа, статус, сумма, email.
- Сделайте повторную смену статуса и убедитесь, что дубли не создаются.
Если CRM возвращает HTTP 200, но данные не обновляются, проблема обычно в формате тела запроса или в том, что endpoint ожидает другой ключ авторизации. Если приходит 401 или 403, сначала проверяйте заголовки и секрет.
Частые ошибки и как их исправить
Хук выбран не тот
Иногда разработчики пытаются ловить изменение через сохранение заказа вручную и используют слишком общий хук. Для синхронизации статуса удобнее woocommerce_order_status_changed, потому что он дает старый и новый статус сразу.
Отправка идет на каждый статус, включая служебные
WooCommerce использует не только бизнес-статусы. Если не ограничить список, CRM будет получать события вроде pending или on-hold, которые ей не нужны. Решение простое: фильтровать статусы перед отправкой.
Секрет хранится прямо в коде темы
Это работает, но неудобно для поддержки. Лучше вынести endpoint и ключ в настройки плагина или хотя бы в wp-config.php через константы. Так проще менять доступы без правки шаблонов.
Нет логирования ошибок
Без логов вы не поймете, где именно ломается цепочка: DNS, SSL, таймаут, 500 на стороне CRM или неверный JSON. Для боевого сайта логирование нужно хотя бы на время запуска.
Синхронизация тормозит оформление заказа
Если CRM отвечает медленно, лучше не вешать тяжелую логику на момент оформления. Для таких случаев обычно выносят отправку в очередь или хотя бы отправляют только после смены статуса менеджером, а не в момент checkout.
Безопасность и производительность
Вебхук — это не только удобство, но и точка риска. Не отправляйте в CRM лишние персональные данные, если они не нужны для бизнес-процесса. Минимальный набор полей снижает и нагрузку, и последствия утечки.
- используйте HTTPS для endpoint;
- проверяйте ответ сервера и не считайте любой ответ успехом;
- не храните секреты в открытом репозитории;
- ограничьте список статусов, которые реально должны уходить наружу;
- если запросов много, подумайте о буферизации, а не об отправке в каждом хукe синхронно.
Если у вас уже есть набор технических правок для WooCommerce и сайта в целом, часть задач по чистке дублей, отключению лишнего и ускорению админки удобно закрывать через Clearfy Pro: https://wpshop.ru/plugins/clearfy?utm_source=wpone.ru&utm_medium=article&utm_campaign=woocommerce-sinhronizaciya-statusa-zakaza-s-vneshnej-crm. Но саму синхронизацию статусов лучше оставлять в прозрачном коде, который можно быстро проверить и доработать.
Если нужно, на этой же схеме можно построить отправку не только статуса, но и состава заказа, комментария менеджера или кастомных полей. Главное — не расширять payload без необходимости и сразу проверять, как CRM реагирует на новые поля.