Skip to main content
Every run px0 performs - manual, scheduled, or a px0 brain ask - leaves a record: the inputs it resolved, the guideline versions it inlined, every tool call with its timing, and the outcome.
That opens an interactive browser over those records, so finding a run, reading what it did, and rerunning it are one session instead of three commands with ids copy-pasted between them.

The list view

Newest first, one row per run:
[write] marks any run that called a write tool - something that posted, commented, or sent. It is the fastest way to find the run that touched the outside world. A run started with --dry-run is labelled as a rehearsal, so a stubbed run is never mistaken for one that really posted. Run ids are run_<UTC date>-<UTC time>-<random>, so they sort chronologically and never collide. Failed rows are the only ones coloured, so a screen full of runs shows you its problems before you read a word of it. The header counts visible rows against the total, and the line under it names whichever filters are actually in effect - so you are never confused about why a run you expected is missing.

The detail view

Enter on a row shows the whole record:
Three things here are worth knowing: The rendered prompt is recovered from the run’s raw log - the actual text the model received, with inputs interpolated and guidelines inlined. Raw logs are deleted on the retention schedule (logs.retention_days), so for an old run you will see not available -- log retention removed it instead. The record itself is kept far longer than the log, which is why the summary survives even when the verbatim prompt does not. Guidelines inlined names each file with the version used, not just the filename. If a guideline changed after this run, that difference is visible right here - and it is the single most common explanation for “this used to work”. Timings are per tool call, so a slow run tells you which tool was slow rather than leaving you to guess.

The same data without the TUI

Every view has a plain-text equivalent, which is what you want in a script or a pipe:
runs list --running checks each in-flight marker against the process table before reporting it, so a run that crashed does not show up as one that has been going for days. runs cancel sends SIGTERM, which lets the run finalize its record as failed; --force sends SIGKILL instead, which leaves the record as it was last written, so reach for it only when the run is not responding. runs open differs from runs output: output prints the text recorded on the run, open reads the file on disk, so it shows what is there now if something changed it since. To apply retention outside the daemon’s nightly pass - the only way it happens at all on a store that never installs the daemon:
Runs that called a write tool are never pruned, regardless of age. px0 runs list and the TUI’s list view render row text from the same formatter, so what you grep is exactly what you saw on screen. px0 runs with no terminal to draw on - piped, or in CI - falls back to that plain listing instead of failing. Only the current store’s runs are listed. Records carry the store that produced them, which is what makes PX0_HOME isolate history even though logs.path defaults to one directory shared by every store on the machine. Records written before that stamp existed are shown rather than hidden. --since takes a relative age: 12h, 7d, or 2w. A leading minus is accepted too, so the -7d the TUI suggests works here as well.

Reading a failed run

Failures are recorded, not discarded - px0 persists the record before reporting the error, so you can always go back and read what happened. Work through it in this order:
1

Find it

2

Read the record

The failure names the stage that failed and, for an input failure, which input. An unauthorized app includes the consent URL in the reason.
3

Read the prompt it actually sent

Open the run in px0 runs and look at the rendered prompt. Guideline text that reads oddly, or an input that resolved to nothing, is usually visible immediately.
4

Fix and confirm

Edit the workflow, then rerun by hand with --dry-run before letting the schedule pick it up again.

Saying whether it was any good

The one thing no record can infer is whether what a run produced was worth having. A digest that runs green every week and comes back useless looks perfect in every field px0 has.
The mark is stored on the run’s own record and shows in the listing as [good] or [bad]. Press m on a run’s detail screen to do the same thing from the browser - which is where you have just read what it produced, and the only moment you know.
The note is the part that matters. “Bad” says a run was wrong; “it missed the two PRs I actually reviewed” says how - and that sentence is what px0 workflows improve argues from and what px0 memory suggest reads for standing facts.

What a run did, as data

One JSON object per thing that happened. This is the machine-readable account of a run - which turn called which tool, what each cost, whether a call was allowed - and it is what px0 workflows health reads, rather than the raw log.
Tool argument names are recorded, never their values. A tool’s arguments routinely carry the content of the work - a message body, a file path, a search string - and the event stream is meant to be the part of a run that is safe to keep.

Rolled up by workflow

How many runs each workflow had, how many failed, how many you marked bad, and the median duration. Arithmetic over the records - no model call, no network. For one workflow in detail, and for what its runs say is wrong with it, see Improving a workflow.

How long records are kept

A run leaves three artifacts behind, and they are deliberately different things. The record is the run’s summary, kept for a year, and is what every listing and every analysis reads. The raw log is the full prompt and reply text, kept for a fortnight, and is for a person reading one run. The event stream is the machine-readable account, kept alongside the log. Nothing derives a verdict from the raw log, because the raw log is usually gone. Retention is applied by the daemon’s nightly pass. Without the daemon running, nothing is deleted. Runs that called a write tool are exempt regardless of age: what they did cannot be undone by forgetting it.