KQ-1650 · HEARTBEAT/LEDGER

Heartbeat Ledger

A monitor for scheduled jobs that check in: each row is a job, its owner, a strip of recent check-ins drawn as slim bars whose height is the run's length (on time, late, failed, and a hatched slot wherever a run never arrived) and its next deadline. A new check-in drops into the head of its strip on springs.recoil while the strip rolls one slot left on springs.glide; past its deadline a job wears a ring that runs down its grace on a linear tween between readings of the now prop, and if the grace runs out the row tips into a warning tint that sweeps in on glide while its dot turns into a warning glyph on springs.snap. It is a role="grid" with one roving cell: arrows move, P pauses, M mutes, Enter opens the last run, and Enter on a strip steps into it to pick an older run.

KQ-1650 · HEARTBEAT/LEDGER

Fernworks nightly

6 jobs · 1 due

01:52 now

P pauses a job, M mutes it, Enter opens its last run. Enter on the history steps into it.

Invoice exportEvery 15 min · IP, Every 15 min, owner Ines Park
in 10mdue 02:01, next check-in due in 10 minutes, at 02:01
Ledger closeNightly at 02:00 · TR, Nightly at 02:00, owner Tomas Reyes
in 10mdue 02:02, next check-in due in 10 minutes, at 02:02
Search reindexHourly at :05 · AM, Hourly at :05, owner Ada Moreau
in 16mdue 02:07, next check-in due in 16 minutes, at 02:07
Seed inventory syncEvery 30 min · KM, Every 30 min, owner Kofi Mensah
in 18mdue 02:10, next check-in due in 18 minutes, at 02:10
Backup snapshotNightly at 01:30 · ML, Nightly at 01:30, owner Mara Lind
12m gracedue 01:33, due 18 minutes ago, 12 minutes of grace left
Certificate checkEvery 6 hours · JA, Every 6 hours, owner Joel Achebe
Pausedlast 21:02, paused
On timeLateFailedMissed

01:52 utc · 6 jobs · 1 due · 0 missed

Install

One command — the source lands in your repo. Or copy it from the Code tab.

$ pnpm dlx shadcn@latest add @kinetiq/heartbeat-ledger

Props

stripLength
number
default 24
How many beats each history strip shows at wide widths; narrow widths always show the last ten.
density
"compact" | "cozy" | "roomy"
default "cozy"
Row height and bar size.
accent
string
default "var(--accent-bright)"
On-time ticks, grace rings and the clock, any CSS colour.
jobs
HeartbeatJob[]
default defaultHeartbeatJobs
The jobs: { id, name, schedule, every, grace, lastCheckIn?, owner, beats, typical? } with beats { id, at, status, duration } oldest first.
now
number
default defaultHeartbeatNow
The time every deadline is judged against, in ms; the host advances it and the clock is never read.
paused / defaultPaused
string[]
default — / []
Paused job ids, controlled or initial.
onPause
(job: HeartbeatJob, paused: boolean) => void
default —
Fires from the button or the P key, with whether the job is now paused.
muted / defaultMuted
string[]
default — / []
Muted job ids, controlled or initial.
onMute
(job: HeartbeatJob, muted: boolean) => void
default —
Fires from the button or the M key, with whether the job's alerts are now muted.
onOpenRun
(job: HeartbeatJob, beat: HeartbeatBeat | null) => void
default —
A run was opened: Enter or a press on the job, or a beat picked in its strip; null when the job has never run.
status
"ready" | "loading" | "error"
default "ready"
Loading draws skeleton rows with ghost strips; error shows its own state with Retry; an empty jobs list has its own state too.
onRetry
() => void
default —
Retry was pressed after the check-ins failed to load.
title
string
default "Fernworks nightly"
The heading and the grid's accessible name.
formatTime
(ms: number) => string
default HH:MM in UTC
Formats the clock, deadlines and beat times.
height
number
default 520
Height of the surface in px; rows scroll under the pinned header.
disabled
boolean
default false
Nothing can be paused, muted or opened; the surface dims.
className
string
default —
Classes for the outer surface.