---
read_when:
    - Планирование фоновых заданий или пробуждений
    - Подключение внешних триггеров (Webhook, Gmail) к OpenClaw
    - Выбор между Heartbeat и Cron для запланированных задач
sidebarTitle: Scheduled tasks
summary: Запланированные задания, webhooks и триггеры Gmail PubSub для планировщика Gateway
title: Запланированные задачи
x-i18n:
    generated_at: "2026-07-02T08:37:56Z"
    model: gpt-5.5
    postprocess_version: locale-links-v1
    provider: openai
    source_hash: 2f75b8d1e5ac558a02b895e1cd1b92b05af549a2bd63d4ce3ddafcaf9e94b88e
    source_path: automation/cron-jobs.md
    workflow: 16
---

Cron — это встроенный планировщик Gateway. Он сохраняет задания, будит агента в нужное время и может доставлять вывод обратно в канал чата или конечную точку Webhook.

## Быстрый старт

<Steps>
  <Step title="Add a one-shot reminder">
    ```bash
    openclaw cron create "2026-02-01T16:00:00Z" \
      --name "Reminder" \
      --session main \
      --system-event "Reminder: check the cron docs draft" \
      --wake now \
      --delete-after-run
    ```
  </Step>
  <Step title="Check your jobs">
    ```bash
    openclaw cron list
    openclaw cron get <job-id>
    openclaw cron show <job-id>
    ```
  </Step>
  <Step title="See run history">
    ```bash
    openclaw cron runs --id <job-id>
    ```
  </Step>
</Steps>

## Как работает Cron

- Cron выполняется **внутри процесса Gateway** (не внутри модели).
- Определения заданий, состояние выполнения и история запусков сохраняются в общей базе данных состояния SQLite OpenClaw, поэтому перезапуски не теряют расписания.
- При обновлении выполните `openclaw doctor --fix`, чтобы импортировать устаревшие файлы `~/.openclaw/cron/jobs.json`, `jobs-state.json` и `runs/*.jsonl` в SQLite и переименовать их с суффиксом `.migrated`. Некорректные строки заданий пропускаются во время выполнения и копируются в `jobs-quarantine.json` для последующего исправления или проверки.
- `cron.store` по-прежнему задает логический ключ хранилища Cron и путь импорта doctor. После импорта редактирование этого JSON-файла больше не меняет активные задания Cron; вместо этого используйте `openclaw cron add|edit|remove` или RPC-методы Cron в Gateway.
- Все выполнения Cron создают записи [фоновых задач](/ru/automation/tasks).
- При запуске Gateway просроченные задания изолированных ходов агента перепланируются за пределы окна подключения каналов, а не воспроизводятся немедленно, поэтому запуск Discord/Telegram и настройка нативных команд остаются отзывчивыми после перезапусков.
- Одноразовые задания (`--at`) по умолчанию автоматически удаляются после успешного выполнения.
- Изолированные запуски Cron по возможности закрывают отслеживаемые вкладки браузера/процессы для своего сеанса `cron:<jobId>` после завершения запуска, чтобы отсоединенная браузерная автоматизация не оставляла осиротевшие процессы.
- Изолированные запуски Cron, получившие узкое разрешение на самоочистку Cron, все еще могут читать состояние планировщика, самоотфильтрованный список своего текущего задания и историю запусков этого задания, поэтому проверки статуса/Heartbeat могут просматривать собственное расписание без получения более широкого доступа на изменение Cron.
- Изолированные запуски Cron также защищаются от устаревших подтверждающих ответов. Если первый результат — это только промежуточное обновление статуса (`on it`, `pulling everything together` и похожие подсказки), а ни один дочерний субагентский запуск больше не отвечает за финальный ответ, OpenClaw один раз повторно запрашивает фактический результат перед доставкой.
- Изолированные запуски Cron используют структурированные метаданные отказа выполнения из встроенного запуска, включая обертки node-host `UNAVAILABLE`, у которых вложенное сообщение об ошибке начинается с `SYSTEM_RUN_DENIED` или `INVALID_REQUEST`, поэтому заблокированная команда не отображается как успешный запуск, а обычный текст ассистента не считается отказом.
- Изолированные запуски Cron также считают ошибки агента на уровне запуска ошибками задания, даже когда полезная нагрузка ответа не создана, поэтому ошибки модели/провайдера увеличивают счетчики ошибок и запускают уведомления о сбоях, а не очищают задание как успешное.
- Когда изолированное задание хода агента достигает `timeoutSeconds`, Cron прерывает базовый запуск агента и дает ему короткое окно очистки. Если запуск не завершается, очистка, принадлежащая Gateway, принудительно очищает владение сеансом этого запуска до того, как Cron запишет тайм-аут, поэтому поставленная в очередь работа чата не остается за устаревшим обрабатывающим сеансом.
- Если изолированный ход агента зависает до старта runner или до первого вызова модели, Cron записывает тайм-аут с указанием фазы, например `setup timed out before runner start` или `stalled before first model call (last phase: context-engine)`. Эти watchdog-механизмы покрывают встроенных провайдеров и провайдеров на базе CLI до фактического запуска их внешнего CLI-процесса и ограничиваются независимо от длинных значений `timeoutSeconds`, чтобы сбои холодного старта/аутентификации/контекста проявлялись быстро, а не ждали полного бюджета задания.
- Если вы используете системный cron или другой внешний планировщик для запуска `openclaw agent`, оберните его эскалацией жесткого завершения, даже несмотря на то что CLI обрабатывает `SIGTERM`/`SIGINT`. Запуски через Gateway просят Gateway прервать принятые запуски; локальные и встроенные резервные запуски получают тот же сигнал прерывания. Для GNU `timeout` предпочитайте `timeout -k 60 600 openclaw agent ...` вместо простого `timeout 600 ...`; значение `-k` — это аварийный предел супервизора, если процесс не может корректно завершиться. Для systemd units сохраняйте ту же форму, используя сигнал остановки `SIGTERM` плюс окно ожидания, например `TimeoutStopSec`, перед финальным завершением. Если повторная попытка переиспользует `--run-id`, пока исходный запуск Gateway все еще активен, дубликат отображается как выполняющийся, а не запускает второй запуск.

<a id="maintenance"></a>

<Note>
Сверка задач для Cron сначала принадлежит runtime, а во вторую очередь опирается на долговечную историю: активная задача Cron остается живой, пока runtime Cron все еще отслеживает это задание как выполняющееся, даже если старая строка дочернего сеанса все еще существует. Когда runtime перестает владеть заданием и 5-минутное окно ожидания истекает, обслуживание проверяет сохраненные журналы запусков и состояние задания для соответствующего запуска `cron:<jobId>:<startedAt>`. Если эта долговечная история показывает терминальный результат, журнал задач финализируется на ее основе; иначе обслуживание, принадлежащее Gateway, может пометить задачу как `lost`. Офлайн-аудит CLI может восстановиться из долговечной истории, но не считает свой собственный пустой внутрипроцессный набор активных заданий доказательством того, что запуск Cron, принадлежащий Gateway, исчез.
</Note>

## Типы расписаний

| Вид     | Флаг CLI  | Описание                                                |
| ------- | --------- | ------------------------------------------------------- |
| `at`    | `--at`    | Одноразовая временная метка (ISO 8601 или относительная, например `20m`) |
| `every` | `--every` | Фиксированный интервал                                  |
| `cron`  | `--cron`  | 5-польное или 6-польное выражение Cron с необязательным `--tz` |

Временные метки без часового пояса считаются UTC. Добавьте `--tz America/New_York` для планирования по местному времени.

Повторяющиеся выражения на начало часа автоматически распределяются с разбросом до 5 минут, чтобы снизить пики нагрузки. Используйте `--exact`, чтобы принудительно задать точное время, или `--stagger 30s` для явного окна.

### День месяца и день недели используют логику OR

Выражения Cron разбираются [croner](https://github.com/Hexagon/croner). Когда поля дня месяца и дня недели оба не являются wildcard, croner срабатывает, когда совпадает **любое** из полей, а не оба. Это стандартное поведение Vixie cron.

```
# Intended: "9 AM on the 15th, only if it's a Monday"
# Actual:   "9 AM on every 15th, AND 9 AM on every Monday"
0 9 15 * 1
```

Это срабатывает примерно 5-6 раз в месяц вместо 0-1 раза в месяц. Здесь OpenClaw использует стандартное поведение OR от Croner. Чтобы требовать оба условия, используйте модификатор дня недели `+` в Croner (`0 9 15 * +1`) или планируйте по одному полю, а другое проверяйте в промпте или команде задания.

## Стили выполнения

| Стиль           | Значение `--session` | Где выполняется          | Лучше всего для                |
| --------------- | ------------------- | ------------------------ | ------------------------------ |
| Основной сеанс  | `main`              | Выделенная линия пробуждения Cron | Напоминания, системные события |
| Изолированный   | `isolated`          | Выделенный `cron:<jobId>` | Отчеты, фоновые задачи         |
| Текущий сеанс   | `current`           | Привязан во время создания | Повторяющаяся работа с учетом контекста |
| Пользовательский сеанс | `session:custom-id` | Постоянный именованный сеанс | Рабочие процессы, которые строятся на истории |

<AccordionGroup>
  <Accordion title="Main session vs isolated vs custom">
    Задания **основного сеанса** ставят системное событие в очередь линии запуска, принадлежащей Cron, и при необходимости будят Heartbeat (`--wake now` или `--wake next-heartbeat`). Они могут использовать последний контекст доставки целевого основного сеанса для ответов, но не добавляют рутинные ходы Cron в человеческую линию чата и не продлевают свежесть ежедневного/idle-сброса для целевого сеанса. **Изолированные** задания выполняют выделенный ход агента со свежим сеансом. **Пользовательские сеансы** (`session:xxx`) сохраняют контекст между запусками, позволяя рабочим процессам вроде ежедневных стендапов строиться на предыдущих сводках.

    События Cron в основном сеансе — это самодостаточные напоминания системных событий. Они
    не включают автоматически инструкцию "Read
    HEARTBEAT.md" из стандартного промпта Heartbeat. Если повторяющееся напоминание должно обращаться к
    `HEARTBEAT.md`, явно укажите это в тексте события Cron или в
    собственных инструкциях агента.

  </Accordion>
  <Accordion title="What 'fresh session' means for isolated jobs">
    Для изолированных заданий "свежий сеанс" означает новый идентификатор стенограммы/сеанса для каждого запуска. OpenClaw может переносить безопасные предпочтения, такие как настройки thinking/fast/verbose, метки и явно выбранные пользователем переопределения модели/аутентификации, но не наследует окружающий контекст разговора из более старой строки Cron: маршрутизацию канала/группы, политику отправки или очереди, elevation, origin или привязку runtime ACP. Используйте `current` или `session:<id>`, когда повторяющееся задание должно намеренно строиться на том же контексте разговора.
  </Accordion>
  <Accordion title="Runtime cleanup">
    Для изолированных заданий завершение runtime теперь включает best-effort очистку браузера для этого сеанса Cron. Ошибки очистки игнорируются, чтобы фактический результат Cron все равно имел приоритет.

    Изолированные запуски Cron также освобождают любые встроенные экземпляры runtime MCP, созданные для задания, через общий путь очистки runtime. Это соответствует тому, как закрываются клиенты MCP основного сеанса и пользовательского сеанса, поэтому изолированные задания Cron не оставляют утечек дочерних процессов stdio или долгоживущих подключений MCP между запусками.

  </Accordion>
  <Accordion title="Subagent and Discord delivery">
    Когда изолированные запуски Cron координируют субагентов, доставка также предпочитает финальный вывод потомка устаревшему промежуточному тексту родителя. Если потомки все еще выполняются, OpenClaw подавляет это частичное родительское обновление вместо его объявления.

    Для текстовых целей объявления Discord OpenClaw отправляет канонический финальный текст ассистента один раз, вместо того чтобы воспроизводить и потоковые/промежуточные текстовые payload, и финальный ответ. Медиа и структурированные payload Discord по-прежнему доставляются как отдельные payload, чтобы вложения и компоненты не были отброшены.

  </Accordion>
</AccordionGroup>

### Полезные нагрузки команд

Используйте полезные нагрузки команд для детерминированных скриптов, которые должны выполняться внутри планировщика Gateway без запуска изолированного хода агента на базе модели. Командные задания выполняются на хосте Gateway, захватывают stdout/stderr, записывают запуск в историю Cron и переиспользуют те же режимы доставки `announce`, `webhook` и `none`, что и изолированные задания.

<Note>
Командный Cron — это административная поверхность автоматизации Gateway для оператора, а не вызов
`tools.exec` агента. Создание, обновление, удаление или ручной запуск заданий Cron
требует `operator.admin`; запланированные командные запуски позже выполняются внутри
процесса Gateway как эта автоматизация, созданная администратором. Политика exec агента, такая как
`tools.exec.mode`, запросы подтверждения и allowlist инструментов для каждого агента, управляет
видимыми модели exec-инструментами, а не полезными нагрузками командного Cron.
</Note>

```bash
openclaw cron create "*/15 * * * *" \
  --name "Queue depth probe" \
  --command "scripts/check-queue.sh" \
  --command-cwd "/srv/app" \
  --announce \
  --channel telegram \
  --to "-1001234567890"
```

`--command <shell>` сохраняет `argv: ["sh", "-lc", <shell>]`. Используйте `--command-argv '["node","scripts/report.mjs"]'`, когда нужно точное выполнение argv без разбора shell. Необязательные поля `--command-env KEY=VALUE`, `--command-input`, `--timeout-seconds`, `--no-output-timeout-seconds` и `--output-max-bytes` управляют окружением процесса, stdin и ограничениями вывода.

Если stdout не пуст, этот текст является доставленным результатом. Если stdout пуст, а stderr не пуст, доставляется stderr. Если присутствуют оба потока, cron доставляет небольшой блок `stdout:` / `stderr:`. Нулевой код выхода записывает запуск как `ok`; ненулевой код выхода, сигнал, тайм-аут или тайм-аут отсутствия вывода записывает `error` и может запускать оповещения о сбоях. Команда, которая выводит только `NO_REPLY`, использует обычное подавление silent-token cron и ничего не отправляет обратно в чат.

### Параметры payload для изолированных заданий

<ParamField path="--message" type="string" required>
  Текст запроса (обязателен для изолированного режима).
</ParamField>
<ParamField path="--model" type="string">
  Переопределение модели; использует выбранную разрешенную модель для задания.
</ParamField>
<ParamField path="--fallbacks" type="string">
  Список резервных моделей для отдельного задания, например `--fallbacks openrouter/gpt-4.1-mini,openai/gpt-5`. Передайте `--fallbacks ""` для строгого запуска без резервных вариантов.
</ParamField>
<ParamField path="--clear-fallbacks" type="boolean">
  При `cron edit` удаляет переопределение резервных моделей для отдельного задания, чтобы задание следовало настроенному приоритету резервных вариантов. Нельзя сочетать с `--fallbacks`.
</ParamField>
<ParamField path="--clear-model" type="boolean">
  При `cron edit` удаляет переопределение модели для отдельного задания, чтобы задание следовало обычному приоритету выбора модели cron (сохраненное переопределение cron-сессии, если задано, иначе модель агента/по умолчанию). Нельзя сочетать с `--model`.
</ParamField>
<ParamField path="--thinking" type="string">
  Переопределение уровня thinking.
</ParamField>
<ParamField path="--clear-thinking" type="boolean">
  При `cron edit` удаляет переопределение thinking для отдельного задания, чтобы задание следовало обычному приоритету thinking cron. Нельзя сочетать с `--thinking`.
</ParamField>
<ParamField path="--light-context" type="boolean">
  Пропустить внедрение bootstrap-файла рабочей области.
</ParamField>
<ParamField path="--tools" type="string">
  Ограничить инструменты, которые может использовать задание, например `--tools exec,read`.
</ParamField>

`--model` использует выбранную разрешенную модель как основную модель этого задания. Это не то же самое, что переопределение `/model` в чат-сессии: настроенные цепочки резервных вариантов по-прежнему применяются при сбое основной модели задания. Если запрошенная модель не разрешена или не может быть разрешена, cron завершает запуск с явной ошибкой валидации, а не незаметно возвращается к выбору модели агента/по умолчанию для задания.

Задания Cron также могут нести `fallbacks` на уровне payload. Если он присутствует, этот список заменяет настроенную цепочку резервных вариантов для задания. Используйте `fallbacks: []` в payload/API задания, когда нужен строгий запуск cron, который пробует только выбранную модель. Если у задания есть `--model`, но нет ни payload, ни настроенных резервных вариантов, OpenClaw передает явное пустое переопределение резервных вариантов, чтобы основная модель агента не добавлялась как скрытая дополнительная цель повтора.

Предварительные проверки локальных провайдеров проходят по настроенным резервным вариантам перед тем, как пометить запуск cron как `skipped`; `fallbacks: []` оставляет этот путь предварительной проверки строгим.

Приоритет выбора модели для изолированных заданий:

1. Переопределение модели Gmail hook (когда запуск пришел из Gmail и это переопределение разрешено)
2. `model` в payload отдельного задания
3. Выбранное пользователем сохраненное переопределение модели cron-сессии
4. Выбор модели агента/по умолчанию

Быстрый режим также следует разрешенному live-выбору. Если в конфигурации выбранной модели есть `params.fastMode`, изолированный cron использует его по умолчанию. Сохраненное переопределение `fastMode` сессии все равно имеет приоритет над конфигурацией в любую сторону. Автоматический режим использует порог `params.fastAutoOnSeconds` выбранной модели, если он присутствует, по умолчанию 60 секунд.

Если изолированный запуск попадает на live-передачу переключения модели, cron повторяет попытку с переключенным провайдером/моделью и сохраняет этот live-выбор для активного запуска перед повтором. Когда переключение также несет новый профиль аутентификации, cron сохраняет это переопределение профиля аутентификации для активного запуска. Повторы ограничены: после начальной попытки плюс 2 повтора переключения cron прерывает выполнение вместо бесконечного цикла.

Перед тем как изолированный запуск cron войдет в runner агента, OpenClaw проверяет доступные конечные точки локальных провайдеров для настроенных провайдеров `api: "ollama"` и `api: "openai-completions"`, у которых `baseUrl` является loopback, адресом частной сети или `.local`. Если эта конечная точка недоступна, запуск записывается как `skipped` с понятной ошибкой провайдера/модели вместо начала вызова модели. Результат для конечной точки кэшируется на 5 минут, поэтому множество наступивших заданий, использующих один и тот же недоступный локальный сервер Ollama, vLLM, SGLang или LM Studio, совместно используют одну небольшую проверку вместо создания шквала запросов. Пропущенные из-за предварительной проверки провайдера запуски не увеличивают backoff ошибок выполнения; включите `failureAlert.includeSkipped`, если нужны повторяющиеся уведомления о пропусках.

## Доставка и вывод

| Режим      | Что происходит                                                                       |
| ---------- | ------------------------------------------------------------------------------------- |
| `announce` | Доставить итоговый текст целевому получателю через fallback, если агент не отправил |
| `webhook`  | Отправить payload события завершения POST-запросом на URL                            |
| `none`     | Нет fallback-доставки runner                                                         |

Используйте `--announce --channel telegram --to "-1001234567890"` для доставки в канал. Для тем форумов Telegram используйте `-1001234567890:topic:123`; OpenClaw также принимает принадлежащую Telegram сокращенную форму `-1001234567890:123`. Непосредственные вызывающие стороны RPC/config могут передавать `delivery.threadId` как строку или число. Цели Slack/Discord/Mattermost должны использовать явные префиксы (`channel:<id>`, `user:<id>`). Идентификаторы комнат Matrix чувствительны к регистру; используйте точный ID комнаты или форму `room:!room:server` из Matrix.

Когда доставка announce использует `channel: "last"` или опускает `channel`, цель с префиксом провайдера, такая как `telegram:123`, может выбрать канал до того, как cron вернется к истории сессии или единственному настроенному каналу. Только префиксы, объявленные загруженным Plugin, являются селекторами провайдера. Если `delivery.channel` задан явно, префикс цели должен называть того же провайдера; например, `channel: "whatsapp"` с `to: "telegram:123"` отклоняется, вместо того чтобы позволить WhatsApp интерпретировать Telegram ID как номер телефона. Префиксы типа цели и сервиса, такие как `channel:<id>`, `user:<id>`, `imessage:<handle>` и `sms:<number>`, остаются синтаксисом цели, принадлежащим каналу, а не селекторами провайдера.

Для изолированных заданий доставка в чат является общей. Если доступен маршрут чата, агент может использовать инструмент `message`, даже когда задание использует `--no-deliver`. Если агент отправляет сообщение настроенной/текущей цели, OpenClaw пропускает fallback-объявление. В противном случае `announce`, `webhook` и `none` управляют только тем, что runner делает с итоговым ответом после хода агента.

Когда агент создает изолированное напоминание из активного чата, OpenClaw сохраняет сохраненную live-цель доставки для fallback-маршрута announce. Внутренние ключи сессий могут быть в нижнем регистре; цели доставки провайдера не реконструируются из этих ключей, когда доступен текущий контекст чата.

Неявная доставка announce использует настроенные allowlist каналов для валидации и перенаправления устаревших целей. Подтверждения из DM pairing-store не являются получателями fallback-автоматизации; задайте `delivery.to` или настройте запись `allowFrom` канала, когда запланированное задание должно проактивно отправлять сообщения в DM.

## Язык вывода

Задания Cron не выводят язык ответа из канала, локали или предыдущих
сообщений. Поместите правило языка в запланированное сообщение или шаблон:

```bash
openclaw cron edit <jobId> \
  --message "Суммируй обновления. Ответь на китайском; оставь URL, код и названия продуктов без изменений."
```

Для файлов шаблонов сохраняйте языковую инструкцию в сформированном промпте и
проверяйте, что заполнены placeholders, такие как `{{language}}`, до запуска задания. Если
вывод смешивает языки, задайте правило явно, например: "Используйте китайский
для повествовательного текста и сохраняйте технические термины на английском."

Уведомления о сбоях используют отдельный путь назначения:

- `cron.failureDestination` задает глобальное значение по умолчанию для уведомлений о сбоях.
- `job.delivery.failureDestination` переопределяет его для отдельного задания.
- Если не задано ни одно из них, а задание уже доставляет сообщения через `announce`, уведомления о сбоях теперь используют этот основной целевой объект announce как резервный.
- `delivery.failureDestination` поддерживается только для заданий `sessionTarget="isolated"`, если основной режим доставки не `webhook`.
- `failureAlert.includeSkipped: true` включает для задания или глобальной политики оповещений cron повторяющиеся оповещения о пропущенных запусках. Пропущенные запуски ведут отдельный счетчик последовательных пропусков, поэтому они не влияют на backoff при ошибках выполнения.

## Примеры CLI

<Tabs>
  <Tab title="Однократное напоминание">
    ```bash
    openclaw cron add \
      --name "Calendar check" \
      --at "20m" \
      --session main \
      --system-event "Next heartbeat: check calendar." \
      --wake now
    ```
  </Tab>
  <Tab title="Повторяющееся изолированное задание">
    ```bash
    openclaw cron create "0 7 * * *" \
      "Summarize overnight updates." \
      --name "Morning brief" \
      --tz "America/Los_Angeles" \
      --session isolated \
      --announce \
      --channel slack \
      --to "channel:C1234567890"
    ```
  </Tab>
  <Tab title="Переопределение модели и thinking">
    ```bash
    openclaw cron add \
      --name "Deep analysis" \
      --cron "0 6 * * 1" \
      --tz "America/Los_Angeles" \
      --session isolated \
      --message "Weekly deep analysis of project progress." \
      --model "opus" \
      --thinking high \
      --announce
    ```
  </Tab>
  <Tab title="Вывод Webhook">
    ```bash
    openclaw cron create "0 18 * * 1-5" \
      "Summarize today's deploys as JSON." \
      --name "Deploy digest" \
      --webhook "https://example.invalid/openclaw/cron"
    ```
  </Tab>
  <Tab title="Вывод команды">
    ```bash
    openclaw cron create "*/15 * * * *" \
      --name "Queue depth probe" \
      --command "scripts/check-queue.sh" \
      --command-cwd "/srv/app" \
      --announce \
      --channel telegram \
      --to "-1001234567890"
    ```
  </Tab>
</Tabs>

## Webhooks

Gateway может предоставлять HTTP-эндпоинты Webhook для внешних триггеров. Включите в конфигурации:

```json5
{
  hooks: {
    enabled: true,
    token: "shared-secret",
    path: "/hooks",
  },
}
```

### Аутентификация

Каждый запрос должен включать токен hook через заголовок:

- `Authorization: Bearer <token>` (рекомендуется)
- `x-openclaw-token: <token>`

Токены в строке запроса отклоняются.

<AccordionGroup>
  <Accordion title="POST /hooks/wake">
    Добавить системное событие в очередь для основного сеанса:

    ```bash
    curl -X POST http://127.0.0.1:18789/hooks/wake \
      -H 'Authorization: Bearer SECRET' \
      -H 'Content-Type: application/json' \
      -d '{"text":"New email received","mode":"now"}'
    ```

    <ParamField path="text" type="string" required>
      Описание события.
    </ParamField>
    <ParamField path="mode" type="string" default="now">
      `now` или `next-heartbeat`.
    </ParamField>

  </Accordion>
  <Accordion title="POST /hooks/agent">
    Запустить изолированный ход агента:

    ```bash
    curl -X POST http://127.0.0.1:18789/hooks/agent \
      -H 'Authorization: Bearer SECRET' \
      -H 'Content-Type: application/json' \
      -d '{"message":"Summarize inbox","name":"Email","model":"openai/gpt-5.4"}'
    ```

    Поля: `message` (обязательно), `name`, `agentId`, `wakeMode`, `deliver`, `channel`, `to`, `model`, `fallbacks`, `thinking`, `timeoutSeconds`.

  </Accordion>
  <Accordion title="Сопоставленные hooks (POST /hooks/<name>)">
    Пользовательские имена hook разрешаются через `hooks.mappings` в конфигурации. Сопоставления могут преобразовывать произвольные payloads в действия `wake` или `agent` с помощью шаблонов или преобразований кода.
  </Accordion>
</AccordionGroup>

<Warning>
Держите эндпоинты hook за loopback, tailnet или доверенным reverse proxy.

- Используйте выделенный токен хука; не переиспользуйте токены аутентификации Gateway.
- Держите `hooks.path` на выделенном подпути; `/` отклоняется.
- Задайте `hooks.allowedAgentIds`, чтобы ограничить, на какого эффективного агента может нацеливаться хук, включая агента по умолчанию, когда `agentId` опущен.
- Оставляйте `hooks.allowRequestSessionKey=false`, если вам не нужны сеансы, выбираемые вызывающей стороной.
- Если вы включаете `hooks.allowRequestSessionKey`, также задайте `hooks.allowedSessionKeyPrefixes`, чтобы ограничить допустимые формы ключей сеанса.
- Полезные нагрузки хуков по умолчанию оборачиваются границами безопасности.

</Warning>

## Интеграция Gmail PubSub

Подключите триггеры входящих Gmail к OpenClaw через Google PubSub.

<Note>
**Требования:** CLI `gcloud`, `gog` (gogcli), включенные хуки OpenClaw, Tailscale для публичной конечной точки HTTPS.
</Note>

### Настройка мастером (рекомендуется)

```bash
openclaw webhooks gmail setup --account openclaw@gmail.com
```

Это записывает конфигурацию `hooks.gmail`, включает пресет Gmail и использует Tailscale Funnel для push-конечной точки.

### Автозапуск Gateway

Когда задано `hooks.enabled=true` и установлен `hooks.gmail.account`, Gateway при запуске стартует `gog gmail watch serve` и автоматически продлевает наблюдение. Задайте `OPENCLAW_SKIP_GMAIL_WATCHER=1`, чтобы отказаться от этого.

### Ручная одноразовая настройка

<Steps>
  <Step title="Выберите проект GCP">
    Выберите проект GCP, которому принадлежит OAuth-клиент, используемый `gog`:

    ```bash
    gcloud auth login
    gcloud config set project <project-id>
    gcloud services enable gmail.googleapis.com pubsub.googleapis.com
    ```

  </Step>
  <Step title="Создайте тему и предоставьте Gmail доступ для push">
    ```bash
    gcloud pubsub topics create gog-gmail-watch
    gcloud pubsub topics add-iam-policy-binding gog-gmail-watch \
      --member=serviceAccount:gmail-api-push@system.gserviceaccount.com \
      --role=roles/pubsub.publisher
    ```
  </Step>
  <Step title="Запустите наблюдение">
    ```bash
    gog gmail watch start \
      --account openclaw@gmail.com \
      --label INBOX \
      --topic projects/<project-id>/topics/gog-gmail-watch
    ```
  </Step>
</Steps>

### Переопределение модели Gmail

```json5
{
  hooks: {
    gmail: {
      model: "openrouter/meta-llama/llama-3.3-70b-instruct:free",
      thinking: "off",
    },
  },
}
```

## Управление заданиями

```bash
# List all jobs
openclaw cron list

# Get one stored job as JSON
openclaw cron get <jobId>

# Show one job, including resolved delivery route
openclaw cron show <jobId>

# Edit a job
openclaw cron edit <jobId> --message "Updated prompt" --model "opus"

# Force run a job now
openclaw cron run <jobId>

# Force run a job now and wait for its terminal status
openclaw cron run <jobId> --wait --wait-timeout 10m --poll-interval 2s

# Run only if due
openclaw cron run <jobId> --due

# View run history
openclaw cron runs --id <jobId> --limit 50

# View one exact run
openclaw cron runs --id <jobId> --run-id <runId>

# Delete a job
openclaw cron remove <jobId>

# Agent selection (multi-agent setups)
openclaw cron create "0 6 * * *" "Check ops queue" --name "Ops sweep" --session isolated --agent ops
openclaw cron edit <jobId> --clear-agent
```

`openclaw cron run <jobId>` возвращается после постановки ручного запуска в очередь. Используйте `--wait` для хуков завершения, скриптов обслуживания или другой автоматизации, которая должна блокироваться до завершения поставленного в очередь запуска. Режим ожидания опрашивает точно возвращенный `runId`; он завершается с `0` для статуса `ok` и с ненулевым кодом для `error`, `skipped` или тайм-аута ожидания.

Инструмент агента `cron` возвращает компактные сводки заданий (`id`, `name`, `enabled`, `nextRunAtMs`, `scheduleKind`, `lastRunStatus`) из `cron(action: "list")`; используйте `cron(action: "get", jobId: "...")` для одного полного определения задания. Прямые вызывающие стороны Gateway могут передать `compact: true` в `cron.list`; если опустить это поле, сохраняется существующий полный ответ с предпросмотрами доставки.

`openclaw cron create` является псевдонимом для `openclaw cron add`, а новые задания могут использовать позиционное расписание (`"0 9 * * 1"`, `"every 1h"`, `"20m"` или ISO-метку времени), за которым следует позиционный промпт агента. Используйте `--webhook <url>` в `cron add|create` или `cron edit`, чтобы отправлять полезную нагрузку завершенного запуска POST-запросом на HTTP-конечную точку. Доставку Webhook нельзя сочетать с флагами доставки в чат, такими как `--announce`, `--channel`, `--to`, `--thread-id` или `--account`. В `cron edit` флаги `--clear-channel`, `--clear-to`, `--clear-thread-id` и `--clear-account` снимают эти поля маршрутизации по отдельности (каждый отклоняется вместе со своим соответствующим флагом установки), что отличается от `--no-deliver`, отключающего резервную доставку раннера.

<Note>
Примечание о переопределении модели:

- `openclaw cron add|edit --model ...` изменяет выбранную модель задания.
- Если модель разрешена, точно этот провайдер/модель попадает в изолированный запуск агента.
- Если она не разрешена или не может быть разрешена, cron завершает запуск ошибкой с явной ошибкой валидации.
- Исправления полезной нагрузки API `cron.update` могут задать `model: null`, чтобы очистить сохраненное переопределение модели задания.
- `openclaw cron edit <job-id> --clear-model` очищает это переопределение из CLI (тот же эффект, что и исправление `model: null`) и не может сочетаться с `--model`.
- Настроенные цепочки резервирования по-прежнему применяются, потому что cron `--model` является основной моделью задания, а не переопределением `/model` сеанса.
- `openclaw cron add|edit --fallbacks ...` задает `fallbacks` полезной нагрузки, заменяя настроенные резервные варианты для этого задания; `--fallbacks ""` отключает резервирование и делает запуск строгим. `openclaw cron edit <job-id> --clear-fallbacks` очищает переопределение для отдельного задания.
- Обычный `--model` без явного или настроенного списка резервных вариантов не проваливается к основной модели агента как к тихой дополнительной цели повтора.

</Note>

## Конфигурация

```json5
{
  cron: {
    enabled: true,
    store: "~/.openclaw/cron/jobs.json",
    maxConcurrentRuns: 8,
    retry: {
      maxAttempts: 3,
      backoffMs: [60000, 120000, 300000],
      retryOn: ["rate_limit", "overloaded", "network", "server_error"],
    },
    webhookToken: "replace-with-dedicated-webhook-token",
    sessionRetention: "24h",
    runLog: { maxBytes: "2mb", keepLines: 2000 },
  },
}
```

`maxConcurrentRuns` ограничивает и запланированную отправку cron, и выполнение изолированного агентского хода, а по умолчанию равно 8. Изолированные агентские ходы cron внутренне используют выделенную очередь выполнения `cron-nested`, поэтому увеличение этого значения позволяет независимым LLM-запускам cron продвигаться параллельно, а не только запускать их внешние оболочки cron. Общая не-cron очередь `nested` этим параметром не расширяется.

`cron.store` — это логический ключ хранилища и устаревший путь импорта doctor. Запустите `openclaw doctor --fix`, чтобы импортировать существующие JSON-хранилища в SQLite и архивировать их; будущие изменения cron должны проходить через CLI или API Gateway.

Отключить cron: `cron.enabled: false` или `OPENCLAW_SKIP_CRON=1`.

<AccordionGroup>
  <Accordion title="Поведение повторов">
    **Повтор одноразового запуска**: временные ошибки (ограничение скорости, перегрузка, сеть, ошибка сервера) повторяются до 3 раз с экспоненциальной задержкой. Постоянные ошибки отключают сразу.

    **Повтор периодического запуска**: экспоненциальная задержка (от 30 с до 60 мин) между повторами. Задержка сбрасывается после следующего успешного запуска.

  </Accordion>
  <Accordion title="Обслуживание">
    `cron.sessionRetention` (по умолчанию `24h`) удаляет записи сеансов изолированных запусков. `cron.runLog.keepLines` ограничивает сохраняемые строки истории запусков SQLite для каждого задания; `maxBytes` сохраняется для совместимости конфигурации со старыми файловыми журналами запусков.
  </Accordion>
</AccordionGroup>

## Устранение неполадок

### Лестница команд

```bash
openclaw status
openclaw gateway status
openclaw cron status
openclaw cron list
openclaw cron runs --id <jobId> --limit 20
openclaw system heartbeat last
openclaw logs --follow
openclaw doctor
```

<AccordionGroup>
  <Accordion title="Cron не срабатывает">
    - Проверьте `cron.enabled` и переменную окружения `OPENCLAW_SKIP_CRON`.
    - Убедитесь, что Gateway работает непрерывно.
    - Для расписаний `cron` проверьте часовой пояс (`--tz`) относительно часового пояса хоста.
    - `reason: not-due` в выводе запуска означает, что ручной запуск был проверен с `openclaw cron run <jobId> --due`, и срок задания еще не наступил.

  </Accordion>
  <Accordion title="Cron сработал, но доставки нет">
    - Режим доставки `none` означает, что резервная отправка раннером не ожидается. Агент все еще может отправлять напрямую с помощью инструмента `message`, когда доступен маршрут чата.
    - Отсутствующая/недействительная цель доставки (`channel`/`to`) означает, что исходящая отправка была пропущена.
    - Для Matrix скопированные или устаревшие задания с приведенными к нижнему регистру идентификаторами комнат `delivery.to` могут завершаться ошибкой, потому что идентификаторы комнат Matrix чувствительны к регистру. Отредактируйте задание до точного значения `!room:server` или `room:!room:server` из Matrix.
    - Ошибки аутентификации канала (`unauthorized`, `Forbidden`) означают, что доставка была заблокирована учетными данными.
    - Если изолированный запуск возвращает только тихий токен (`NO_REPLY` / `no_reply`), OpenClaw подавляет прямую исходящую доставку, а также подавляет резервный путь сводки из очереди, поэтому в чат ничего не публикуется.
    - Если агент должен сам написать пользователю, проверьте, что у задания есть пригодный маршрут (`channel: "last"` с предыдущим чатом или явный канал/цель).

  </Accordion>
  <Accordion title="Cron или Heartbeat, похоже, мешает rollover в стиле /new">
    - Свежесть ежедневного и простоящего сброса не основана на `updatedAt`; см. [Управление сеансами](/ru/concepts/session#session-lifecycle).
    - Пробуждения Cron, запуски Heartbeat, уведомления exec и учет Gateway могут обновлять строку сеанса для маршрутизации/статуса, но они не продлевают `sessionStartedAt` или `lastInteractionAt`.
    - Для устаревших строк, созданных до появления этих полей, OpenClaw может восстановить `sessionStartedAt` из заголовка сеанса transcript JSONL, когда файл все еще доступен. Устаревшие строки простоя без `lastInteractionAt` используют это восстановленное время начала как базовую точку простоя.

  </Accordion>
  <Accordion title="Подводные камни часовых поясов">
    - Cron без `--tz` использует часовой пояс хоста Gateway.
    - Расписания `at` без часового пояса считаются UTC.
    - Heartbeat `activeHours` использует настроенное разрешение часового пояса.

  </Accordion>
</AccordionGroup>

## Связанные материалы

- [Автоматизация](/ru/automation) — все механизмы автоматизации в одном обзоре
- [Фоновые задачи](/ru/automation/tasks) — журнал задач для выполнений cron
- [Heartbeat](/ru/gateway/heartbeat) — периодические ходы основного сеанса
- [Часовой пояс](/ru/concepts/timezone) — конфигурация часового пояса
