fabro run invocation creates a timestamped directory under ~/.fabro/runs/:
YYYYMMDD-{run_id}, where run_id is the ULID assigned to the run. You can override the location with --run-dir.
Root-level files
| File | Format | When written | Description |
|---|---|---|---|
manifest.json | JSON | Run start | Run metadata — run_id, workflow_name, goal, start_time, node_count, edge_count, run_branch, base_sha, labels |
graph.fabro | DOT | Run start | Copy of the workflow graph |
run.pid | Text | Run start | Process ID of the running CLI process. Presence indicates the run is active; an orphaned file indicates a crash. |
run.toml | TOML | Run start | Copy of the original workflow file (only when the workflow is defined in TOML) |
progress.jsonl | JSONL | Continuous | Event stream — one JSON object per line for every significant event (stage starts, completions, tool calls, retries, etc.). See Observability for the full event catalog. |
live.json | JSON | Continuous | Current execution state snapshot, overwritten on each event. Used for live monitoring. |
checkpoint.json | JSON | After each node | Crash recovery state — current_node, completed_nodes, node_retries, context_values, node_outcomes, next_node_id, git_commit_sha, failure signatures. See Checkpoints. |
conclusion.json | JSON | Run end | Final result — status, duration_ms, failure_reason, final_git_commit_sha. Only present when the run completes (not for crashed or interrupted runs). |
final.patch | Diff | Run end | Git diff from base_sha to final HEAD. Only present in git checkpoint mode. |
retro.json | JSON | Run end | Post-run retrospective analysis — smoothness_rating, learnings, friction_points, stages. Omitted if --no-retro is passed. See Retros. |
cli.log | Text | Continuous | Per-run tracing log. Contains the same tracing output as the daily log file, scoped to this run. |
nodes/ subdirectory
Each node execution writes artifacts into nodes/{node_id}/. When a node is retried, subsequent visits use nodes/{node_id}-visit_{N}/ (where N starts at 2).
Every node gets a status.json after completion containing status, notes, failure_reason, and timestamp. The remaining files depend on the handler type:
Agent and prompt nodes:
| File | Description |
|---|---|
prompt.md | The full prompt sent to the LLM |
response.md | The LLM’s response text |
status.json | Execution status with routing outcome |
| File | Description |
|---|---|
script_invocation.json | Command metadata — command, language, timeout_ms |
stdout.log | Standard output |
stderr.log | Standard error |
script_timing.json | Timing info — duration_ms, exit_code, timed_out |
| File | Description |
|---|---|
diff.patch | Git diff of changes made during this stage |
child/ directory containing a full run structure (manifest, checkpoint, nodes, etc.).
Other directories
worktree/ — When running in git checkpoint mode, Fabro creates a Git worktree here as the working directory for agents and commands.
assets/ — Test artifacts collected from the execution environment (Playwright reports, JUnit XML, Cypress screenshots/videos). Located at worktree/assets/ for local runs or within node directories for remote sandbox runs.
Browsing runs
Usefabro ps to scan the runs directory and display a table of all runs with their status, workflow name, and timestamps. Pass --json for machine-readable output.