Why Traditional Monitoring Can't Watch Cron Jobs
HTTP monitors poll your servers from the outside, but cron jobs, queue workers, and scheduled tasks run inside your infrastructure with no public endpoint. If a nightly billing reconciliation silently stops running, an HTTP check will never notice. Heartbeat monitoring flips the model: your job pings FourSight when it completes, and FourSight alerts you when the ping doesn't arrive on time.
A Dead-Man's Switch for Your Infrastructure
The mental model that makes heartbeat monitoring click is the dead-man's switch: the safety mechanism on a train that requires the driver to keep applying pressure — the moment the pressure stops, the brakes engage automatically. Heartbeat monitoring applies the same inversion to your jobs. Instead of asking 'can I reach the server?' (which says nothing about whether last night's backup ran), the system demands continuous proof of life: your job must actively report success, on schedule, forever. Silence is treated as failure. This inversion is what catches the failure modes ordinary monitoring can't: the crontab line deleted in a bad deploy, the server that was decommissioned while its jobs quietly moved nowhere, the scheduler daemon that stopped after a reboot, the job that runs but exits early before doing its work. In every one of those cases nothing is 'down' — there's simply an absence where work should be. A dead-man's switch is the only monitor that hears absence.
How Heartbeat Monitoring Works
When you create a heartbeat monitor in FourSight you receive a unique ping URL. Your job sends a simple HTTP request to that URL every time it completes successfully. FourSight tracks the expected interval and a configurable grace period. If a ping doesn't arrive before the deadline, FourSight opens an incident and notifies your team through your configured escalation policy.
Fixed-Interval Mode
Set an expected interval (e.g. every 5 minutes, every hour) and a grace window. This is ideal for jobs that run on simple repeating schedules like queue consumers, health-check scripts, or data-sync workers.
Cron-Expression Mode
Provide a standard 5-field cron expression (e.g. '30 2 * * *' for 2:30 AM daily). FourSight calculates the next expected run time dynamically, making it perfect for jobs with complex schedules like 'every weekday at 9 AM' or 'first Sunday of the month'.
Grace Period & Miss Threshold
The grace period absorbs normal jitter — a job that's 20 seconds late on a 5-minute schedule shouldn't wake anyone up. The miss threshold lets you require multiple consecutive missed pings before alerting, reducing noise from transient issues.
Setting Up Your First Heartbeat Monitor
In the FourSight dashboard, create a new monitor and select the Heartbeat type. Choose your schedule mode, set your interval or cron expression, and configure a sensible grace period. FourSight generates a unique ping URL you'll add to the end of your job.
# At the end of your cron job script:
curl -fsS --retry 3 https://ping.foursight.cloud/hb/<YOUR_TOKEN>
# Example crontab entry — daily DB backup at 3 AM
0 3 * * * /opt/scripts/backup-db.sh && curl -fsS --retry 3 https://ping.foursight.cloud/hb/<YOUR_TOKEN>
Copy-Paste: PowerShell & Windows Task Scheduler
Windows scheduled tasks fail even more silently than cron — Task Scheduler will happily report 'The operation completed successfully' about launching a script that then crashed. Put the ping at the end of the script itself, inside your error handling, so it only fires when the work actually finished.
# end of your scheduled .ps1 script — ping only on success
try {
# ... your script logic ...
Invoke-RestMethod -Uri "https://ping.foursight.cloud/hb/<YOUR_TOKEN>" `
-Method Get -TimeoutSec 10 | Out-Null
} catch {
Write-Error "Job failed: $_"
exit 1 # no ping fires -> FourSight alerts on the missed heartbeat
}
Monitoring a Commercial SaaS?
FourSight's free plan includes 10 commercial-safe monitors with multi-region validation — free forever, no card.
Start Monitoring FreeCopy-Paste: GitHub Actions Scheduled Workflows
GitHub Actions cron workflows have a notorious silent-failure mode: scheduled workflows are automatically disabled after 60 days of repository inactivity, and schedules can be delayed or skipped during high-load periods. GitHub emails you about some failures — but never about a workflow that simply stopped being scheduled. A heartbeat ping as the final step catches both.
name: nightly-job
on:
schedule:
- cron: "0 3 * * *" # 03:00 UTC daily
jobs:
run:
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v4
- name: Do the actual work
run: ./scripts/nightly-job.sh
# Runs only if every previous step succeeded
- name: Report heartbeat to FourSight
run: curl -fsS --retry 3 "https://ping.foursight.cloud/hb/${{ secrets.FOURSIGHT_HEARTBEAT_TOKEN }}"
Copy-Paste: node-cron and In-Process Schedulers
In-process schedulers like node-cron, node-schedule, or APScheduler add an extra failure layer: the schedule dies whenever the host process does. A crashed Node service takes every scheduled task with it, and nothing external knows those jobs existed. The heartbeat covers both the job logic and the process hosting it.
import cron from "node-cron";
// Every hour at :05 — sync exchange rates
cron.schedule("5 * * * *", async () => {
try {
await syncExchangeRates();
// Ping only after the work succeeded
await fetch("https://ping.foursight.cloud/hb/<YOUR_TOKEN>", {
signal: AbortSignal.timeout(10_000),
});
} catch (err) {
console.error("sync failed:", err);
// no ping -> missed heartbeat -> alert
}
});
How Do You Tune the Grace Period?
The grace period is the slack between a job's expected check-in and the moment FourSight declares it missing. Too tight and normal runtime variance pages you for nothing; too loose and a genuinely dead job goes unreported for hours. Two rules cover most cases. For frequent jobs (every 1–15 minutes), set the grace period to roughly 20–50% of the interval — enough to absorb scheduler jitter and a slow network call. For infrequent jobs (hourly to daily), size the grace period from the job's runtime instead: worst-observed runtime plus 50%, because a nightly warehouse refresh that takes 12 minutes on a normal Monday may take 45 at month-end. If you're pinging at the end of the job (recommended), remember the deadline is schedule time + runtime + grace — budget for all three.
| Job schedule | Typical runtime | Suggested grace period | Reasoning |
|---|---|---|---|
| Every 5 min (queue worker) | Seconds | 1–2 min | Absorb jitter; still alert within minutes |
| Hourly sync | 1–5 min | 10–15 min | Runtime variance + one slow run |
| Nightly backup, 3 AM | 10–45 min | 60 min | Worst-case runtime + 50% |
| Weekly report, Mon 6 AM | ~10 min | 2–3 hours | Infrequent job — favor certainty over speed |
| Month-end billing run | Varies widely | Worst case + 50% | Consider a 2-miss threshold too |
Common Use Cases
Heartbeat monitoring is useful anywhere a process should run on a predictable schedule.
Database Backups
Append a ping to your pg_dump or mysqldump script. If tonight's backup doesn't complete, you'll know by morning — not during the next disaster recovery drill.
Queue Workers & Consumers
Have your worker ping FourSight on each processing cycle. If the worker crashes or the queue stalls, the missed heartbeat triggers an alert before messages pile up.
Billing & Invoice Generation
Scheduled billing runs are revenue-critical. A missed invoice cycle can cascade into payment failures and churn. Heartbeat monitoring catches the silence.
Data Sync & ETL
Nightly data imports, warehouse refreshes, and third-party API syncs all benefit from heartbeat checks that confirm successful completion.
Best Practices
Place the ping call after your job's success criteria, not at the start — a ping that fires before the work happens monitors your scheduler, not your job. Use --retry flags on curl (or explicit timeouts in code) so a transient network blip doesn't register as a dead job. Treat ping URLs as secrets: anyone holding one can fake a healthy heartbeat, so keep tokens in environment variables or secret stores, not in committed code. For long jobs, consider two monitors — one pinged at start, one at completion — to distinguish 'never started' from 'started but hung.' And pair every revenue-critical heartbeat with an escalation policy so a missed 3 AM backup pages the on-call engineer instead of sitting unread in a Slack channel.