Skip to content
LastPing
GUIDE · SYSTEMD · FREE

Monitor systemd timers: success, failure, and silence

ExecStartPost pings on success. An OnFailure unit pings on failure. And when the timer stops firing entirely (masked unit, lost enablement, machine down), LastPing alerts on the silence. Three small unit files, copy-paste below. Free, no monitor cap.

Your assistant can do this for you

Monitor my systemd timers with LastPing

On this page
  1. systemd remembers failures. It doesn't report them.
  2. Setup: three unit files
  3. What this catches
  4. Questions people ask

systemd remembers failures. It doesn't report them.

A failed unit sits patiently in systemctl --failed, waiting for a human who isn't coming.

Failure mode 01

Failed units nobody lists

The unit fails, the state is recorded, the journal has the traceback, and unless someone runs systemctl --failed on that exact host, nobody ever learns about it.

Failure mode 02

The timer that stops firing

A unit left disabled after a rebuild, a missing Persistent=true so a powered-off window is skipped forever, a rename that broke WantedBy: the timer doesn't fail. It just stops existing.

Failure mode 03

The journal as a write-only medium

Errors land in the journal with perfect fidelity and zero reach. Journald is superb at recording what happened, and mute about telling you.

Setup: three unit files

The example monitors a nightly backup; rename to match your job. If curl lives elsewhere on your distro, check with which curl.

Create a heartbeat monitor

In the console, create a monitor matching the timer's schedule (a simple interval or a cron expression with an IANA timezone) plus a grace window, and copy the ping URL.

https://ping.lastping.dev/<your-monitor-id>

The service: ping on success

For Type=oneshot, ExecStartPost runs only after ExecStart exits successfully, so the ping means the job actually worked:

# /etc/systemd/system/backup.service
[Unit]
Description=Nightly backup
OnFailure=backup-fail.service

[Service]
Type=oneshot
ExecStart=/usr/local/bin/backup.sh
ExecStartPost=/usr/bin/curl -fsS -m 10 --retry 3 -o /dev/null https://ping.lastping.dev/<your-monitor-id>

The failure reporter: alert immediately

OnFailure starts this unit whenever the service enters a failed state. It's optional (a failed run also sends no success ping, so the grace window would alert anyway), but /fail makes it immediate:

# /etc/systemd/system/backup-fail.service
[Unit]
Description=Report backup failure to LastPing

[Service]
Type=oneshot
ExecStart=/usr/bin/curl -fsS -m 10 --retry 3 -o /dev/null https://ping.lastping.dev/<your-monitor-id>/fail

The timer

Persistent=true runs a missed activation at the next boot instead of skipping it silently:

# /etc/systemd/system/backup.timer
[Unit]
Description=Run nightly backup at 03:00

[Timer]
OnCalendar=*-*-* 03:00:00
Persistent=true

[Install]
WantedBy=timers.target

Enable and test the whole loop once

sudo systemctl daemon-reload
sudo systemctl enable --now backup.timer

# run the service once by hand — the ping should land in the console
sudo systemctl start backup.service

# confirm the next scheduled activation
systemctl list-timers backup.timer

Optional: catch hung runs too

An ExecStartPre ping to /start arms overrun detection: if the matching success doesn't arrive inside the grace window, LastPing opens an incident while the job is still wedged:

ExecStartPre=/usr/bin/curl -fsS -m 10 --retry 3 -o /dev/null https://ping.lastping.dev/<your-monitor-id>/start

What this catches

The units report what they can; the silence reports the rest.

  • The service failed: OnFailure pings /fail and you're alerted immediately, journal intact for the post-mortem.
  • The timer stopped firing: disabled unit, broken enablement, masked service. No ping in the expected window → incident.
  • The machine is down: nothing on the host can report that; the absence of the ping does.
  • The job hung: with the /start ping armed, a run that never completes inside grace opens an incident.
  • Recovery: the next successful run closes the incident and sends a recovery notice automatically.

Still on classic cron for some hosts? The cron guide is the same pattern in one crontab line. Backup jobs deserve the fuller start → work → success/fail pattern, or browse all guides.

Questions people ask

Front-loaded answers: the most important fact first.

  • How do I monitor a systemd timer?

    Add ExecStartPost=/usr/bin/curl -fsS -m 10 --retry 3 -o /dev/null https://ping.lastping.dev/<your-monitor-id> to the service unit. For Type=oneshot services, ExecStartPost runs only after ExecStart exits successfully, so the ping means the job actually worked. LastPing expects that ping on the timer’s schedule and alerts when it does not arrive.

  • Does ExecStartPost run if the service fails?

    No. For Type=oneshot services, ExecStartPost commands run only after ExecStart has exited successfully. That's exactly the behavior you want: a failed job sends no success ping, and the missed ping (or the OnFailure unit pinging /fail) raises the alert.

  • How do I get an immediate alert when a systemd service fails?

    Add OnFailure=backup-fail.service to the [Unit] section, where the referenced unit is a oneshot that curls the /fail endpoint. The explicit failure signal opens an incident immediately instead of waiting out the grace window.

  • What if the whole machine is down?

    The timer can't fire and nothing on the host can self-report, but LastPing alerts anyway, because the expected ping never arrives. Absence-based detection is the point: it covers every failure mode, including the ones the machine can't see.

  • systemd timer or cron: does it matter for monitoring?

    No. Both patterns end in the same ping to the same URL; systemd just gives you nicer hooks (ExecStartPost, OnFailure) than a shell &&. The cron guide covers the crontab one-liner.

  • Is systemd timer monitoring free?

    Yes. LastPing is free for individuals with no monitor cap. See how it compares to Healthchecks.io and Cronitor.

FREE FOR INDIVIDUALS · FULLY HOSTED

systemctl --failed is a list of alerts you never got.

Three unit files now beat a journal archaeology session later. First alert wired up in minutes, and LastPing monitors itself the same way.