1С Битрикс · 7 мин чтения

Агенты и cron в Битрикс: фоновые задачи по расписанию

Агенты в Битрикс и cron на сервере - два инструмента для одной задачи: выполнить код в фоне без участия пользователя. За несколько лет работы с проектами на 1С-Битрикс я обычно ставлю связку из обоих механизмов - агенты живут внутри ядра CMS и по умолчанию запускаются при хитах на сайт, а cron дёргает агентское расписание Битрикс напрямую через php_cli, без зависимости от посещаемости. В статье - как настроить агенты и cron в Битрикс так, чтобы фоновые задачи выполнялись по расписанию, а не «когда кто-то случайно зашёл на сайт ночью».

Чем агенты Битрикс отличаются от системного cron

Агент в Битрикс - это PHP-функция, зарегистрированная в таблице b_agent, с полями ACTIVE, INTERVAL и NEXT_EXEC. По умолчанию ядро проверяет эту таблицу на каждом хите: зашёл пользователь на сайт - сработал prolog, сработала проверка агентов, если время пришло - функция выполнилась. Это удобно на старте, потому что не нужен доступ к серверу и crontab, но на сайте с низким трафиком ночью агент с интервалом в час может выполниться с опозданием на несколько часов, а на сайте с высокой посещаемостью - создать пиковую нагрузку, если несколько тяжёлых агентов совпадают по времени с наплывом трафика.

Системный cron работает независимо от посещаемости: он вызывает PHP-скрипт по расписанию через crontab на сервере. Для Битрикс это файл bitrix/php_cli/agents.php, который поднимает ядро в CLI-режиме и вызывает CAgent::CheckAgents() - по сути ту же логику, что и на хите, но без привязки к запросу пользователя.

Критерий Агент на хитах Агент + cron
Точность расписания Зависит от трафика Секунды-минуты
Нагрузка на сайт Пики совпадают с посещаемостью Равномерная, отдельно от хитов
Нужен доступ к серверу Нет Да, для crontab
Подходит для Тестовых и некритичных задач Интеграций, рассылок, синхронизаций

На практике для интернет-магазинов и сервисов с интеграциями (обмен с CRM, статусы доставки, уведомления) я всегда перевожу агенты на cron ещё на этапе настройки продакшена - тестировать логику на хитах можно, но в проде это создаёт непредсказуемую задержку выполнения.

Как зарегистрировать агент в Битрикс: код

Агент регистрируется вызовом CAgent::AddAgent - обычно это делают в install-файле модуля или разово через консоль администратора.

<?php
CAgent::AddAgent(
    "MyAgentSyncCdek();",           // имя функции с ()
    "main",                          // модуль, к которому привязан агент
    "N",                             // период (N — обычный интервальный режим)
    900,                              // интервал в секундах между запусками
    "",                               // дата первого выполнения (пусто — сразу)
    "Y",                              // активен
    date("d.m.Y H:i:s", time() + 900), // время следующего запуска
    100                                // сортировка
);

Сама функция должна быть доступна в момент выполнения (объявлена в подключаемом модулем файле) и обязательно возвращать строку с вызовом самой себя - без этого агент выполнится один раз и отключится:

function MyAgentSyncCdek()
{
    $result = SyncCdekOrderStatuses();

    if (!$result) {
        AddMessage2Log("MyAgentSyncCdek: ошибка синхронизации со СДЭК", "main");
    }

    return "MyAgentSyncCdek();";
}

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

Бесплатный материал

🎁 Полезный скрипт в подарок

Подпишитесь на Telegram - пришлю готовый скрипт по этой теме.

Без спама. Отписка в 1 клик.

Настройка cron для агентского расписания Битрикс

Чтобы агенты не зависели от хитов, в панели администратора идём в Настройки → Агенты и ставим галочку «Использовать crontab» - с этого момента ядро перестаёт проверять таблицу b_agent на каждом запросе пользователя. Дальше на сервере добавляем задачу в crontab:

*/5 * * * * /usr/bin/php /home/bitrix/www/bitrix/php_cli/agents.php >/dev/null 2>&1

Запуск раз в 5 минут - рабочий компромисс для большинства проектов: агент с интервалом 900 секунд (15 минут) выполнится с погрешностью максимум в 5 минут, а нагрузка на сервер от самого cron-вызова минимальна, потому что CheckAgents проверяет таблицу и пропускает всё, для чего время ещё не пришло. Для задач, где важна секундная точность (например, отправка сообщения в момент наступления события), агенты вообще не лучший инструмент - там я обычно ставлю отдельный crontab-вызов конкретного PHP-скрипта или очередь через RabbitMQ.

Важно проверить, что php_cli использует ту же версию PHP и те же настройки php.ini, что и веб-сервер - иначе агент, работающий на сайте, может падать в cron из-за отсутствия расширения или другого memory_limit. На хостингах с несколькими версиями PHP это частая причина, почему «агент вроде настроен, а данные не обновляются».

Частые ошибки при настройке фоновых задач в Битрикс

  • Функция агента не возвращает строку самовызова - агент выполняется один раз и «засыпает» навсегда, оставаясь ACTIVE в базе.
  • Галочка «Использовать crontab» включена, а сам crontab на сервере не настроен - агенты просто перестают выполняться вообще, потому что и хиты их больше не триггерят, и cron не вызывается.
  • Несколько записей в crontab дублируют вызов agents.php - агент с коротким интервалом может выполниться дважды подряд, что критично для операций записи (двойное списание остатков, повторная отправка уведомления).
  • Тяжёлый агент (парсинг большого XML, синхронизация тысяч позиций) упирается в max_execution_time при выполнении через веб-сервер - в php_cli это ограничение обычно не действует, но если запуск идёт через wget или curl на публичный URL, лимит веб-сервера снова в игре.
  • Часовой пояс сервера не совпадает с часовым поясом, который ожидает бизнес-логика - агент, привязанный к «концу рабочего дня», срабатывает не в 18:00, а в 15:00 по UTC.

Мониторинг и логирование выполнения агентов

Проверить, что агент реально отрабатывает, можно прямо в базе - поле LAST_EXEC в таблице b_agent показывает время последнего запуска, а разница между NEXT_EXEC и текущим временем подскажет, накапливается ли отставание. Для продакшен-проектов я обычно добавляю логирование через AddMessage2Log с указанием модуля, чтобы ошибки агентов попадали в общий журнал событий Битрикс и были видны в Настройки → Журнал событий, а не терялись в error_log сервера вперемешку с остальным.

Для критичных интеграций - синхронизация остатков, обмен заказами, статусы оплаты - одного журнала внутри CMS недостаточно: если агент падает молча, узнают об этом обычно клиенты, когда заказ не пришёл. Практика, которая себя оправдала: при ошибке в функции агента дополнительно отправлять сообщение в отдельный Telegram-чат для разработчиков через простого aiogram-бота или вебхук - уведомление приходит за секунды, а не после жалобы клиента. Для части клиентов такие цепочки мониторинга я собираю через автоматизацию в n8n - туда удобно выносить логику ретраев и алертов, не раздувая код самого модуля Битрикс.

Практические примеры: интеграции и уведомления

Синхронизация статусов доставки СДЭК

Типовая задача для интернет-магазина: раз в 15 минут агент опрашивает API СДЭК по номерам активных отправлений и обновляет статус заказа в Битрикс. Делать это на каждом хите бессмысленно - статус доставки не меняется по несколько раз в минуту, а лишние обращения к внешнему API увеличивают риск упереться в лимиты. С cron-расписанием интервал предсказуем, и легко посчитать нагрузку: при 200 активных отправлениях и интервале в 15 минут это около 20 запросов в минуту к API СДЭК, что укладывается в лимиты большинства тарифов.

Уведомления и отчёты

Агент, который раз в сутки в 9:00 собирает сводку по заказам за прошедшие сутки и отправляет её менеджеру в Telegram - ещё один частый запрос. Реализуется тем же агентом с интервалом 86400 секунд и функцией, которая формирует выборку из b_sale_order и дёргает Telegram Bot API. Если отчётов и интеграций набирается много и логика начинает разрастаться внутри модуля Битрикс, часть из них выгоднее вынести за пределы CMS - например, отдельным Python-скриптом по cron на сервере, без нагрузки на ядро Битрикс вообще. Готовые заготовки таких скриптов для типовых интеграций я собираю в библиотеке готовых скриптов.

Когда агентов Битрикс лучше не трогать вообще

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

Чтобы сайт работал без сбоев

Техподдержка

от 15 000 ₽/мес

Подробнее →

Частые вопросы

Чем агент Битрикс отличается от crontab-задачи на сервере?

Агент - это механизм внутри ядра Битрикс: функция регистрируется в таблице b_agent и по умолчанию проверяется на каждом хите сайта. Crontab-задача - системный планировщик Linux, который вызывает скрипт независимо от посещаемости. На практике их комбинируют: агент описывает бизнес-логику и хранится в базе Битрикс, а crontab вызывает bitrix/php_cli/agents.php, чтобы агент выполнялся по расписанию, а не по хитам.

Как проверить, что агент реально выполняется по расписанию?

Посмотреть поля LAST_EXEC и NEXT_EXEC в таблице b_agent - если LAST_EXEC не обновляется, значит выполнение не срабатывает вообще (проблема с crontab или php_cli) либо функция агента падает с ошибкой раньше, чем доходит до записи лога. Второй способ - включить логирование через AddMessage2Log внутри самой функции и смотреть Журнал событий в панели администратора.

Можно ли использовать n8n вместо агентов Битрикс?

Для задач, не завязанных на внутренние сущности Битрикс (каталог, заказы, пользователи), n8n удобнее - там визуально настраивается расписание, ретраи и уведомления об ошибках без написания PHP-кода. Для операций, которые напрямую читают и пишут в таблицы Битрикс через его API (обновление остатков, статусов заказов), агент внутри самой CMS остаётся логичнее, потому что работает в том же окружении и с теми же правами.

Что делать, если агент завершается с ошибкой или зависает?

Первым делом проверить, что функция агента действительно возвращает строку самовызова - без этого агент отключается после первого запуска. Дальше - смотреть логи PHP и Журнал событий Битрикс на предмет исключений, и добавить try/catch внутри функции агента с логированием ошибки, чтобы одно необработанное исключение не блокировало все последующие агенты в цепочке CheckAgents.

Есть задача?

Обсудим в мессенджере

Расскажите, что нужно сделать — отвечу в течение 4 часов в рабочее время. Первая консультация бесплатно.

Самозанятый Калинкин Н. А. · работаю с физлицами и юрлицами

Продолжая пользование настоящим сайтом Вы выражаете своё согласие на обработку Ваших персональных данных (файлов куки) с использованием Yandex.Metrika.
Понятно