KQ-2094 · SPIKE/TRACE
Spike Trace
A workspace's daily usage as bars with anomalous days flagged, where pressing a spike unpacks it: the bar splits into a coloured band per cause and from each band a strand fans out across the chart to its row in a ranked list beside it, drawn by a clip that sweeps from the bar to the list on springs.glide while the rows arrive in a cascade and one line names the biggest cause. Switching between keys, people and prompts re-splits the bar and re-sweeps the strands, and Escape folds it back on the exit ease. The flagged days are a roving set of buttons — Left and Right move between them, Home and End jump, Enter or Space unpacks, Escape folds — and in a narrow container the strands become a stacked bar above the list.
Oct 15 · keys · nightly-evals 61% · 3 flagged
Install
One command — the source lands in your repo. Or copy it from the Code tab.
$ pnpm dlx shadcn@latest add @kinetiq/spike-trace
Props
- days
- SpikeDay[]
- default defaultSpikeDays
- Daily usage, oldest first: { date, total }.
- attributions
- Record<string, SpikeAttribution>
- default defaultSpikeAttributions
- What made each flagged day, by date: { keys, members, prompts } lists of { id, label, amount, detail? }.
- flags
- SpikeFlag[]
- default defaultSpikeFlags
- The days the detector flagged: { date, expected?, note? }. Empty shows the no-spikes state.
- pending
- string[]
- default ["2026-10-17"]
- Flagged dates whose causes are still being computed.
- value / defaultValue
- string | null
- default — / null
- The unpacked date, controlled or initial.
- onSelectSpike
- (date | null, day) => void
- default —
- Fires from the press or key that unpacked a spike, or with null when it folds.
- dimension / defaultDimension
- "keys" | "members" | "prompts"
- default — / "keys"
- What the spike is unpacked by, controlled or initial.
- onDimensionChange
- (dimension) => void
- default —
- Fires from the switch with the new dimension.
- onOpenCause
- (cause, dimension, date) => void
- default —
- A cause's Open button was pressed.
- onFlagExpected
- (date, expected) => void
- default —
- Mark expected was pressed, with the state it asks for. Omit it and the button is not drawn.
- status
- "ready" | "loading" | "error"
- default "ready"
- Usage arrived, is on its way, or failed.
- onRetry
- () => void
- default —
- Try again was pressed after usage failed to load.
- maxCauses
- number
- default 5
- Causes listed before the rest are folded into one row.
- title
- string
- default "Basinworks · usage"
- The panel's heading.
- subtitle
- string
- default "Sep 18 – Oct 17 · tokens a day"
- Under the heading; by default the window and the unit.
- unit
- string
- default "tokens"
- What is counted, in words.
- formatValue
- (amount: number) => string
- default "6.4M", by hand
- How an amount is printed.
- strandStyle
- "ribbon" | "thread" | "step"
- default "ribbon"
- How the strands are drawn: filled ribbons as thick as their share, fine threads, or orthogonal steps.
- flagStyle
- "pin" | "ring" | "band"
- default "pin"
- How a flagged day is marked: a pin above the bar, a ring, or a tinted band behind it.
- accent
- "cobalt" | "plum" | "mint" | "ink" | string
- default "cobalt"
- The spike, the switch and the hue the cause colours turn from.
- disabled
- boolean
- default false
- Read only: spikes cannot be unpacked or marked.
- className
- string
- default —
- Classes for the panel.
| Prop | Type | Default | Description |
|---|---|---|---|
| days | SpikeDay[] | defaultSpikeDays | Daily usage, oldest first: { date, total }. |
| attributions | Record<string, SpikeAttribution> | defaultSpikeAttributions | What made each flagged day, by date: { keys, members, prompts } lists of { id, label, amount, detail? }. |
| flags | SpikeFlag[] | defaultSpikeFlags | The days the detector flagged: { date, expected?, note? }. Empty shows the no-spikes state. |
| pending | string[] | ["2026-10-17"] | Flagged dates whose causes are still being computed. |
| value / defaultValue | string | null | — / null | The unpacked date, controlled or initial. |
| onSelectSpike | (date | null, day) => void | — | Fires from the press or key that unpacked a spike, or with null when it folds. |
| dimension / defaultDimension | "keys" | "members" | "prompts" | — / "keys" | What the spike is unpacked by, controlled or initial. |
| onDimensionChange | (dimension) => void | — | Fires from the switch with the new dimension. |
| onOpenCause | (cause, dimension, date) => void | — | A cause's Open button was pressed. |
| onFlagExpected | (date, expected) => void | — | Mark expected was pressed, with the state it asks for. Omit it and the button is not drawn. |
| status | "ready" | "loading" | "error" | "ready" | Usage arrived, is on its way, or failed. |
| onRetry | () => void | — | Try again was pressed after usage failed to load. |
| maxCauses | number | 5 | Causes listed before the rest are folded into one row. |
| title | string | "Basinworks · usage" | The panel's heading. |
| subtitle | string | "Sep 18 – Oct 17 · tokens a day" | Under the heading; by default the window and the unit. |
| unit | string | "tokens" | What is counted, in words. |
| formatValue | (amount: number) => string | "6.4M", by hand | How an amount is printed. |
| strandStyle | "ribbon" | "thread" | "step" | "ribbon" | How the strands are drawn: filled ribbons as thick as their share, fine threads, or orthogonal steps. |
| flagStyle | "pin" | "ring" | "band" | "pin" | How a flagged day is marked: a pin above the bar, a ring, or a tinted band behind it. |
| accent | "cobalt" | "plum" | "mint" | "ink" | string | "cobalt" | The spike, the switch and the hue the cause colours turn from. |
| disabled | boolean | false | Read only: spikes cannot be unpacked or marked. |
| className | string | — | Classes for the panel. |