Chapter 23: Cron, Heartbeat & Scheduled Tasks
OpenClaw has two complementary systems for running the agent automatically without user interaction: Cron jobs (fire once at a precise scheduled time) and Heartbeats (periodic self-checks that run within the main session). This chapter covers both β when to use each, how to configure them, and how to minimize API costs.
Cron vs Heartbeat: Which to Use?
| Cron | Heartbeat | |
|---|---|---|
| Trigger | Exact scheduled time | Every N minutes, continuously |
| Session | New isolated session each run | Runs inside the main session |
| Use case | One-off reports, briefings, reminders | Ongoing monitoring, ambient awareness |
| Cost | Per-run token cost | Can be very cheap with lightContext |
| Delivery | Any channel or webhook | Sends only when something needs attention |
Part 1: Cron Jobs
What Are Cron Jobs?
A cron job is a pre-defined prompt that fires at an exact scheduled time. The agent processes it like a user message and delivers the response to a configured destination.
Common use cases:
- Daily standup: Summarize yesterday's GitHub activity and Jira tickets every morning
- Status reports: Check server health every hour and alert if something is wrong
- Weekly digest: Compile the week's messages and decisions from Slack into a summary
- Data monitoring: Check a dashboard or database and report anomalies
- Content generation: Create a daily social media post draft every morning
Defining a Cron Job
{
"cron": {
"tasks": [
{
"id": "morning-briefing",
"name": "Morning Team Briefing",
"schedule": "0 8 * * 1-5",
"workspace": "dev-team",
"agent": "balanced",
"prompt": "Summarize: 1) Any GitHub PRs opened or merged in the last 24 hours. 2) Any Jira tickets updated yesterday. 3) Today's date and any calendar events. Be concise.",
"deliverTo": {
"channel": "slack",
"destination": "C01TEAMCHANNEL"
}
}
]
}
}
Cron Schedule Syntax
ββββββ minute (0β59)
β ββββββ hour (0β23)
β β ββββββ day of month (1β31)
β β β ββββββ month (1β12)
β β β β ββββββ day of week (0β7, 0 and 7 = Sunday)
β β β β β
* * * * *
| Schedule | Expression |
|---|---|
| Every minute | * * * * * |
| Every hour | 0 * * * * |
| Every day at 8 AM | 0 8 * * * |
| Weekdays at 9 AM | 0 9 * * 1-5 |
| Every Monday at 10 AM | 0 10 * * 1 |
| First of every month | 0 0 1 * * |
| Every 15 minutes | */15 * * * * |
Delivery Targets
{ "deliverTo": { "channel": "telegram", "destination": "chat_id" } }
{ "deliverTo": { "channel": "slack", "destination": "C01CHANNELID" } }
{ "deliverTo": { "webhook": "https://hooks.example.com/abc", "method": "POST" } }
{ "deliverTo": { "logOnly": true } }
Conditional Delivery
Only deliver when the agent finds something worth reporting:
{
"id": "error-monitor",
"schedule": "*/10 * * * *",
"prompt": "Check /var/log/app.log for the last 10 minutes. Reply CLEAR if no errors, or describe any ERROR entries found.",
"deliverTo": { "channel": "telegram", "destination": "${ADMIN_CHAT_ID}" },
"deliverIf": "response does not contain CLEAR"
}
Task Variables
| Variable | Value |
|---|---|
{{date}} | Today's date (YYYY-MM-DD) |
{{time}} | Current time (HH:MM) |
{{datetime}} | Full ISO datetime |
{{weekday}} | Day name (Monday, Tuesdayβ¦) |
{{week_number}} | ISO week number |
Managing Cron Jobs via CLI
openclaw cron list
openclaw cron run morning-briefing # Test immediately
openclaw cron pause morning-briefing
openclaw cron resume morning-briefing
openclaw cron delete morning-briefing
openclaw cron history morning-briefing
Timezone Configuration
{
"cron": {
"timezone": "Asia/Karachi",
"tasks": [...]
}
}
Error Handling
{
"cron": {
"onError": {
"retry": 3,
"retryDelay": 300,
"alertChannel": "telegram",
"alertDestination": "${ADMIN_CHAT_ID}"
}
}
}
Part 2: Heartbeat
What Is Heartbeat?
Heartbeat is OpenClaw's proactive awareness system. Unlike cron (which fires once and delivers a report), heartbeat runs periodic agent turns inside the main session so the agent can surface anything that needs attention β without spamming you when everything is fine.
The key idea: the agent reads a checklist file (HEARTBEAT.md) at regular intervals. If all is well, it replies HEARTBEAT_OK and you hear nothing. If something needs your attention, it sends you a message.
The Cost Advantage Over Cron
If you have 5 things to monitor every 30 minutes, cron requires 5 separate agent calls Γ 48 runs/day = 240 API calls/day. One heartbeat with 5 items in its checklist = 1 call Γ 48 runs/day = 48 API calls/day β an 80% cost reduction.
Enabling Heartbeat
{
"agents": {
"defaults": {
"heartbeat": {
"every": "30m",
"target": "last",
"activeHours": {
"start": "09:00",
"end": "22:00",
"timezone": "Asia/Karachi"
}
}
}
}
}
| Field | Description |
|---|---|
every | Interval: "30m", "1h", "15m". Set "0m" to disable. |
target | Where to send alerts: "none" (internal only), "last" (last-used channel) |
activeHours | Only run during these hours (with timezone). Silent outside this window. |
The HEARTBEAT_OK Protocol
When the agent has nothing to report, it starts or ends its reply with HEARTBEAT_OK. OpenClaw sees this token and silently drops the message β you receive no notification. Only when something actually needs attention does a message reach you.
The default ackMaxChars is 300: if the reply contains HEARTBEAT_OK and the remaining content is under 300 characters, it's considered an acknowledgment and dropped.
{
"heartbeat": {
"every": "30m",
"ackMaxChars": 300,
"showOk": false,
"showAlerts": true
}
}
The HEARTBEAT.md Checklist
Create ~/.openclaw/HEARTBEAT.md to define what the agent checks on each tick:
# Heartbeat Checklist
Check the following every 30 minutes:
- [ ] Are there any new messages in the admin Telegram group that need a response?
- [ ] Are any GitHub Actions workflows currently failing?
- [ ] Is disk usage on the server above 85%?
- [ ] Are there any Stripe payment failures in the last 30 minutes?
- [ ] Any critical error logs in /var/log/app.log?
If all clear, reply: HEARTBEAT_OK
If anything needs attention, describe it clearly and send an alert.
The agent reads this file on each heartbeat tick. You can update the checklist anytime and the agent picks up the changes on the next tick.
Cost Optimization
For busy gateways, these two settings dramatically reduce heartbeat cost:
{
"heartbeat": {
"every": "30m",
"isolatedSession": true,
"lightContext": true
}
}
| Setting | Effect |
|---|---|
isolatedSession: true | Each heartbeat runs in a fresh session β no conversation history to process. Reduces token cost from ~100K to ~2β5K per run. |
lightContext: true | Only loads HEARTBEAT.md from bootstrap files, not the full config and skill context. |
Use a cheaper model specifically for heartbeats:
{
"agents": {
"my-agent": {
"provider": "anthropic",
"model": "claude-sonnet-4-6",
"heartbeat": {
"model": "claude-haiku-4-5-20251001",
"isolatedSession": true,
"lightContext": true
}
}
}
}
Task-Based Heartbeat Items
Instead of checking everything every tick, schedule individual checklist items on their own intervals:
# HEARTBEAT.md
tasks:
- check: "Any new Stripe failures?"
every: 15m
- check: "Weekly sales summary ready?"
every: 1w
at: "Monday 09:00"
- check: "Server disk usage above 80%?"
every: 1h
Only tasks that are due on the current tick are included in the agent's context, further reducing cost.
Manual Heartbeat Trigger
# Trigger a heartbeat immediately for testing
openclaw system event --text "Run heartbeat now" --mode now
Visibility Controls
{
"heartbeat": {
"showOk": false,
"showAlerts": true,
"useIndicator": true,
"includeReasoning": false
}
}
useIndicator: true shows a small status indicator in the Control UI even when HEARTBEAT_OK β a visual pulse that confirms the agent is alive without sending notifications.
Choosing: Cron or Heartbeat?
Use cron when:
- You need a report delivered at an exact time (daily briefing at 9 AM)
- The task has a clear end (generate this week's summary)
- You want isolated, independent task runs
Use heartbeat when:
- You need continuous ambient awareness (is anything wrong right now?)
- You want to consolidate multiple monitoring checks into one efficient call
- You only want to be notified when something actually needs attention
Use both together for complete coverage: heartbeat for ongoing monitoring, cron for scheduled reports.
Next: Chapter 24 β Building Custom Skills β How to write your own skills from scratch and integrate any API or service into your OpenClaw gateway.