Skip to main content

Focused Agentic Context Toolkit — Spec Kit + RPI for Claude Code

Project description

FACT — Focused Agentic Context Toolkit

A harness that turns Claude Code into an agent that follows Spec Kit + RPI by default, with a local dashboard for progress, tokens, and cost — and a hook-driven audit layer that pauses the workflow on real security / architecture / quality issues (including missing tests) until the human approves.

Status: v0.1 (private repo). Battle-tested on a 46-task greenfield FastAPI project with continuous security & quality audits.


Table of contents


What is FACT

FACT is the glue between three independent pieces:

  1. Spec Kit — GitHub's spec-driven development toolkit. Constitution → Spec → Plan → Tasks → Implement.
  2. RPI (Research-Plan-Implement) — HumanLayer's discipline: stay under the 40% context window, fork context with sub-agents, write semantic summaries at every phase boundary.
  3. Skills — Anthropic's procedural-knowledge format. FACT ships nine base skills and pulls domain skills from skills.sh on demand for audits.

It runs alongside Claude Code, never wrapping it. Hooks observe the session and feed three things:

  • a local dashboard showing the kanban of stories, token cost, and the file tree,
  • a session-state file that survives crashes so the agent can resume cleanly tomorrow,
  • a hook-driven audit layer that triggers security / architecture / quality reviews via sub-agents loaded with domain skills, and pauses the workflow until the human approves.

Install

Prerequisites

Tool Why
Python 3.10+ FACT and its hooks (Claude Code calls FACT's Python helpers directly — no shell required, including on Windows)
Claude Code on PATH the agent harness FACT plugs into
git repo operations + Spec Kit
gh (only while the repo is private) gh auth login is the simplest way to authenticate git for the install
uv or pipx to install FACT in an isolated env

specify-cli (Spec Kit) is auto-installed on first fact init.

From a fresh machine — macOS

# 1. Homebrew (skip if already installed)
/bin/bash -c "$(curl -fsSL https://raw.githubusercontent.com/Homebrew/install/HEAD/install.sh)"

# 2. Prerequisites
brew install python git uv
# Claude Code: download the desktop installer from https://claude.com/claude-code

# 3. Install FACT (pick the line that matches your situation — see below)
uv tool install fact-toolkit                                                    # PyPI (once published)
# or, while the repo is private / for unreleased dev builds:
# brew install gh && gh auth login
# uv tool install --from git+https://github.com/holaPymbu/fact.git fact-toolkit

From a fresh machine — Windows (PowerShell)

# 1. Prerequisites via winget
winget install --id Python.Python.3.12 -e
winget install --id Git.Git -e
# Claude Code: download from https://claude.com/claude-code

# 2. uv (recommended over pipx — avoids the broken-launcher problem when Python is upgraded)
powershell -ExecutionPolicy ByPass -c "irm https://astral.sh/uv/install.ps1 | iex"

# >>> Close and reopen PowerShell so PATH refreshes <<<

# 3. Install FACT
uv tool install fact-toolkit                                                    # PyPI (once published)
# or, while the repo is private:
# winget install --id GitHub.cli -e ; gh auth login
# uv tool install --from git+https://github.com/holaPymbu/fact.git fact-toolkit

FACT hooks are pure Python — no bash, no Git Bash on PATH required.

Why not pipx on Windows? pipx installs a pipx.exe shim hard-coded to one Python install. If you upgrade or reinstall Python the shim breaks with Unable to create process using ...python.exe. uv doesn't have this problem. If you must use pipx, sidestep the shim: python -m pipx install ....

Already have the prerequisites? Pick one:

Option A — uv tool (recommended)

uv tool install fact-toolkit                                                    # PyPI
# or for unreleased dev builds:
uv tool install --from git+https://github.com/holaPymbu/fact.git fact-toolkit

uv handles the isolated environment for you.

Option B — pipx

pipx install fact-toolkit                                                       # PyPI
# or:
pipx install git+https://github.com/holaPymbu/fact.git

Option C — clone for development

gh repo clone holaPymbu/fact ~/.fact
python3 -m venv ~/.fact/.venv
~/.fact/.venv/bin/pip install -e ~/.fact
echo "alias fact='~/.fact/.venv/bin/fact'" >> ~/.zshrc

After install, fact --help should work in any directory.

Updating

uv tool upgrade fact-toolkit                          # Option A
pipx upgrade fact-toolkit                             # Option B
git -C ~/.fact pull                                   # Option C

After updating FACT itself, run fact upgrade inside any project to refresh its bundled skills, commands, and hooks.

Maintainers: see CONTRIBUTING.md for the release process (PyPI trusted publishing, version bumps, yanking).


Quickstart

In a new directory (greenfield) or an existing repo (brownfield):

cd my-project/
fact init           # one-time setup. Creates .specify/, .claude/, CLAUDE.md.
                    # Auto-installs specify-cli. Starts the dashboard.
claude              # open Claude Code in the same directory
> /fact-start       # picks workflow (greenfield/brownfield/demo) and begins

fact init opens the dashboard at http://localhost:7842. Keep that tab open while you work; it updates in real time as the agent edits files and tasks close.


Dashboard tour

FACT dashboard

A single-page local app on port 7842. Four zones, all live:

Header (top)

  • BrandFACT • <project-name> • <phase>. Phase pill reflects the current Spec Kit phase (constitution, specify, plan, tasks, implement, done).
  • TASKS<done> / <total> aggregated across the visible scope (one feature or all features).
  • TOKENS — total tokens read from the Claude Code transcript, formatted as K/M. Hover to see the input / output / cache breakdown.
  • COST — total session cost in USD, computed from pricing.json. If a model wasn't priced, it's flagged with ?.
  • SAVED VS OPUS — counterfactual: what the workload would have cost if every sub-agent had been Opus. The bigger this number, the more the Haiku/Sonnet sub-agent strategy is paying off.

Sidebar (left)

  • Files tree — every .md file in the project, recursive. Click any to open it in a markdown-rendered modal. Folders are collapsible; defaults expand .specify/, .specify/specs/, .specify/fact/sessions/, .specify/memory/. Ignored automatically: node_modules, .venv, .git, __pycache__, dist, build, *.egg-info, etc.
  • By model — token spend grouped by model (opus-4-7, sonnet-4-6, haiku-4-5). Cost + total tokens per model. Hover for the input/output/cache split.

Kanban (center)

Stories go into Pending / In Progress / Done columns. A story is one of:

Kind Source Visual
foundation the project's Constitution alone yellow border, foundation badge
workflow per-feature pre-implement tasks yellow border, workflow badge
user_story a tasks.md section labeled User Story N, enriched with the title from spec.md blue border, US N badge, optional P1/P2/P3 priority pill
phase any other tasks.md section (Setup, Foundational, Polish, …) gray border, phase badge

Each card shows:

  • a feature badge (which feature it belongs to, e.g. 001·tea),
  • the kind badge + optional priority pill,
  • a counter pill done/total,
  • a slim progress bar (done | in-progress | pending),
  • three count pills ✓ N done · ● N in progress · ○ N pending.

Click a card to open the story detail modal — it lists every task underneath with chips for tags (P, US1, REVIEW, …), files referenced (clickable, opens the file viewer), and dependencies (clickable, jumps to that task's detail).

In-progress signal

When the agent is currently working in a story, the card has:

  • a pulsing blue glow around the border (CSS keyframes, 2.4s),
  • a blinking blue dot next to the kind badge,
  • a started Xm ago footer that updates every 20 seconds.

If a [P] task is delegated to a sub-agent in a worktree, that specific task pulses violet instead of blue, and the card shows a ⤵ subagent · model chip indicating which model is running it.

Toolbar above the kanban

  • Search — matches story title or any field of any task in it (id, title, file, tag, dependency). Tip: press / from anywhere to focus the search.
  • Feature picker — switches between features, or All features (default when there are >1).
  • Filter dropdown — grouped: story kind (User Story / Phase / Workflow / Foundation), priority (P1 / P2 / P3), and task tag (P, US1, US2, …).
  • Hide workflow — toggles foundation + workflow cards off, so you only see real implementation stories.
  • tags? — opens the tag legend explaining P, US N, REVIEW, BLOCKED, etc.

Footer

A live status line: live · updated HH:MM:SS when the WebSocket is connected, reconnecting… when it's down. The dashboard auto-reconnects.


The workflow

FACT is human-in-the-loop by design. The agent never blasts through phases — at every meaningful gate, it stops and asks. Below is the full path from "empty directory" to "feature done", with every user-input gate marked.

flowchart TD
    Start(["fact init → claude → /fact-start"]) --> Resume{prior session<br/>state on disk?}
    Resume -->|yes| Pick["fact-onboarding asks:<br/>continue or start fresh?"]
    Resume -->|no| Type{project type?}
    Pick -->|YOU pick| Type

    Type -->|Greenfield| Disc["fact-discovery<br/>Socratic Q&A,<br/>one question at a time"]
    Type -->|Brownfield| Res["fact-research<br/>7 parallel mappers"]
    Type -->|Demo| Tiny["tinyspec extension<br/>skip discovery + clarify"]

    Disc -->|YOU shape it| Vision["Vision draft"]
    Vision -->|YOU approve, max 2 iterations| Const
    Res --> ResMd["research.md"]
    ResMd -->|YOU validate| Const
    Tiny --> Plan

    Const["speckit.constitution"]
    Const --> Spec["speckit.specify → spec.md"]
    Spec --> Clar["speckit.clarify"]
    Clar -->|YOU resolve ambiguities| Plan["speckit.plan → plan.md"]
    Plan -->|YOU review the plan| Gate{Pre-implement<br/>audit gate}
    Gate -->|critical findings| Plan
    Gate -->|clean| Tasks["speckit.tasks → tasks.md"]

    Tasks --> Loop["For each task<br/>(see 'Inside the implementation loop' below)"]
    Loop --> AuditEdit["per-edit audit<br/>Haiku · security/quality"]
    AuditEdit -->|YOU decide on findings| More{more tasks<br/>in user story?}
    More -->|yes| Loop
    More -->|no| AuditUS["per-user-story audit<br/>Sonnet × 3 · sec/arch/qual"]
    AuditUS -->|YOU decide on findings| Next{more user<br/>stories?}
    Next -->|yes| Loop
    Next -->|no| Done(["Feature done"])

    Done -. opt-in .-> FactAudit["/fact-audit all<br/>full review + run test suite"]

    classDef user fill:#fff3cd,stroke:#856404,color:#000
    classDef gate fill:#f8d7da,stroke:#721c24,color:#000
    class Pick,Disc,Vision,Res,ResMd,Clar,Plan,AuditEdit,AuditUS user
    class Gate gate

Yellow boxes = your input. Red diamond = blocking gate.

Where you give input

Stage What you do
Onboarding Pick greenfield / brownfield / demo. If FACT detects prior session state, also pick: continue or start fresh.
Discovery (greenfield) Answer ~7 topics, one at a time: what to build, who for, what problem, 3-5 v1 features, references, constraints, stack. You can redirect any time ("first tell me about X").
Vision draft (greenfield) Read the draft and iterate (max 2 rounds). The agent pushes back on scope creep — "is this v1 or are you imagining v2?".
Research validation (brownfield) Read research.md, flag what's missing or wrong.
Constitution & spec Approve / revise the principles + spec the agent produces.
Clarify The agent surfaces ambiguities; you answer them in chat.
Plan review Read plan.md before tasks decomposition. fact-rpi-harness §6 explicitly stops here.
Audit gate (pre-implement) If there are critical findings on the plan, you decide: revise plan, override (with logged reason), or rollback.
Per-task audits After each task, the per-edit audit fires. On findings: fix automatically / fix manually / override / rollback.
[P] parallel tasks Tasks marked [P] in tasks.md are delegated to sub-agents in their own worktrees and reviewed in two stages (spec-compliance → code-quality). On needs_rework, you decide: re-dispatch, fix in main, or accept divergence.
End-of-user-story audit Larger 3-dimension review. Same approval flow.
Compaction (60% context) When context fills, the agent proposes 3 options: /compact, close+reopen, or push through. You pick.
/fact-audit all Anytime, run a full review on demand.

Inside the implementation loop

The Loop node above is one task. Internally each task can take two shapes — sequential (the main agent does it) or parallel (a [P]-tagged task delegated to a sub-agent in a worktree). FACT uses sub-agents in two distinct ways during implementation:

  1. Context-forking sub-agents (always available, every task): when the main agent needs to read a lot to act on a little — find call sites, summarize tests, look up library docs — it spawns a short-lived Haiku/Sonnet sub-agent that returns 10-30 lines of distilled findings. The main agent stays focused on the change.
  2. Task-delegation sub-agents (only for [P]-tagged tasks): independent tasks that don't share state can run in parallel, each in its own git worktree, each driven by its own sub-agent.
flowchart TD
    Task[/Task line in tasks.md/]
    Task --> P{"tagged [P]?"}

    P -->|no| TddSeq["fact-tdd:<br/>RED → GREEN → REFACTOR"]
    TddSeq --> CodeSeq["implement<br/>(forks Haiku/Sonnet sub-agents<br/>for codebase lookups, doc reads,<br/>test summaries while coding)"]
    CodeSeq --> VfySeq["fact-verify checklist"]
    VfySeq --> Mark["mark x in tasks.md"]

    P -->|yes| Spawn["spawn sub-agent<br/>in its own worktree<br/>(model per fact-rpi-harness §3)"]
    Spawn --> SubRun["sub-agent runs the task<br/>(applies fact-tdd inside)"]
    SubRun --> Stage1["Stage 1 review<br/>Haiku · spec-compliance<br/>against tasks.md + plan.md"]
    Stage1 --> Stage2["Stage 2 review<br/>Sonnet · code-quality<br/>diff review"]
    Stage2 --> Mark

    Mark --> AuditE["per-edit audit<br/>Haiku · security/quality"]
    AuditE --> Next([next task])

    classDef user fill:#fff3cd,stroke:#856404,color:#000
    class VfySeq,Stage1,Stage2,AuditE user

The dashboard surfaces the difference visually: sequential work pulses blue on the active card; [P] worktree sub-agent work pulses violet, with a ⤵ subagent · model chip on the card so you can see which model is doing what.

Cost discipline notes (from fact-rpi-harness §3 and §8):

  • Lookup sub-agents: Haiku (~10× cheaper than Opus). Pass model="haiku" explicitly — without it sub-agents inherit Opus and cost balloons.
  • Synthesis sub-agents: Sonnet (~5× cheaper than Opus).
  • Stage 1 spec-compliance reviews: Haiku (cheap pattern-match).
  • Stage 2 code-quality reviews: Sonnet (judgement work).
  • The two-stage review typically adds < 5% to total session token cost and catches real bugs the main agent would have merged silently.

The three project types

Greenfield (new project)

The agent loads fact-discovery. You'll have a short, Socratic conversation — one question per message, with room to redirect. The topics it needs to leave the conversation having covered:

  1. What you want to build (one paragraph).
  2. For whom (target users, not "everyone").
  3. What problem it solves.
  4. Scope v1 — 3-5 core features.
  5. References — projects you admire / want to avoid.
  6. Constraints — budget, deadline, deployment, language.
  7. Stack preference (or it suggests after the vision draft).

After every answer, the agent decides: dig deeper, pivot to a topic you opened, or move on. If you say "wait, first I want to talk about X", it follows you. Six exchanges is usually enough.

Then the vision draft, your approval, and Spec Kit:

speckit.constitution   → 4-6 principles derived from your vision
speckit.specify        → first spec.md
speckit.clarify        → ambiguities surfaced; you answer
speckit.plan           → tech stack, architecture, code snippets
[ pre-implement audit gate ]   ← MANDATORY (see Audits)
speckit.tasks          → decompose plan into T-NNN tasks
speckit.implement      → write code, task by task

Brownfield (existing repo)

The agent loads fact-research. It spawns 7 parallel sub-agents (Haiku/Sonnet) that map, in one pass:

  • Folder structure
  • Stack & dependencies (pyproject.toml, package.json, etc.)
  • Code conventions (3-5 representative files)
  • Main modules / entry points
  • Test framework & coverage shape
  • Build & deploy (CI configs, Dockerfile, scripts)
  • Existing docs (README, ARCHITECTURE.md, ADRs)

Result: a research.md under 200 lines. You read it and flag what's missing or wrong. Then constitution + delta spec + plan + audit gate

  • tasks + implement, same as greenfield from there.

If the repo already has an AGENTS.md / CLAUDE.md / GEMINI.md, the agent absorbs its domain knowledge into the constitution and replaces the old file with a one-paragraph pointer back to .specify/memory/constitution.md.

Demo (quick experiment)

Uses the tinyspec Spec Kit extension. Skips discovery and clarify to ship a single throwaway from idea → plan → implement. Useful for spike work where you don't want the full ceremony.

Session summaries between phases

Between every phase, the agent writes a short summary to .specify/fact/sessions/<UTC>.md (What was done, What was decided, What's pending / next). These power continuity — if the session crashes or you close at any point, the next session picks up from the last summary.


Audits

FACT runs continuous audits driven by hooks. Hooks are pure triggers — they never run linters or audit logic themselves. When a hook fires, it emits a structured prompt that pauses the workflow and instructs the agent to load the fact-audit skill. The skill then orchestrates the actual review using sub-agents loaded with domain skills from skills.sh.

Edit / Stop                                        Agent next turn
    │                                                    │
    ▼                                                    ▼
Hook fires  ─►  emits structured trigger  ─►  Agent loads fact-audit
                  + exits with code 2                    │
                                                         ▼
                                              Spawns sub-agents per
                                              dimension, each loaded
                                              with a domain skill
                                              from skills.sh
                                                         │
                                                         ▼
                                              Aggregates findings,
                                              shows them verbatim
                                              to the user
                                                         │
                                                         ▼
                                              User picks: fix /
                                              manually / override /
                                              rollback
                                                         │
                                                         ▼
                                              Workflow resumes

Three triggers

Trigger When Sub-agent Dimensions
source-edit every Edit/Write to .py/.ts/.go/etc Haiku security, quality
task-close edit to tasks.md (likely a task closed) Sonnet security, architecture, quality
session-stop the agent tries to close session Sonnet (×3 parallel) security, architecture, quality (+ runs the project test suite separately)

Tests run via pytest / npm test / cargo test if available. Test failures count as critical.

User-approval flow

When findings of severity ≥ high exist, the agent shows them verbatim and offers four options:

  1. Fix automatically — agent edits the affected files. The next file write re-triggers the audit; it must come back clean for the workflow to resume.
  2. Fix manually — agent pauses while the human edits.
  3. Override — agent records the override + the user's reason in the session summary, then continues.
  4. Rollback — agent proposes the inverse of its last edit; on confirmation, applies it.

Lower-severity findings (medium/low/info) are mentioned in passing without blocking.

Pre-implement gate

Not hook-triggered — explicitly invoked by fact-discovery / fact-research after /speckit.plan and before /speckit.tasks. Three Sonnet sub-agents review the plan against constitution + spec. Critical findings → return to plan iteration.

On demand

> /fact-audit                 # run all dimensions on full session changes
> /fact-audit security        # only that one
> /fact-audit architecture
> /fact-audit quality

Reports

Every audit writes a markdown report to .specify/fact/audits/<UTC>-<dim>.md with YAML frontmatter (severity counts, scope, skill used). They surface in the file tree but not as a dashboard panel — the conversation between agent and user is the canonical audit surface.


CLI reference

Command What it does
fact init Idempotent project setup. Auto-installs specify-cli.
fact init --port 7900 Use a non-default dashboard port.
fact init --no-dashboard Set up the project without starting the dashboard.
fact init --no-speckit Skip the auto-install of specify-cli.
fact dashboard Start (or check) the dashboard server.
fact dashboard --restart Force restart the dashboard.
fact stop Stop the dashboard.
fact doctor Diagnose: what's missing, what's broken.
fact doctor --fix Try to install anything missing (currently: specify-cli).
fact upgrade Re-copy bundled skills / commands / hooks into the project.

Slash commands

Command What it does
/fact-start First time: pick workflow type and begin. Resumed sessions: detects continuity.
/fact-next Continue the current phase or advance to the next.
/fact-status Quick status report in chat (≤10 lines).
/fact-audit Run an audit on demand. Optional arg: security / architecture / quality / all.

Plus all of Spec Kit's /speckit.* commands (constitution, specify, clarify, plan, tasks, implement, verify-tasks, …) which the FACT skills call internally.


Skills shipped with FACT

Skill When loaded What it does
fact-onboarding first thing in /fact-start Detects continuity, asks for project type, hands off to a workflow skill.
fact-rpi-harness always loaded The 40% rule, sub-agent strategy, intentional compaction, session summaries.
fact-discovery greenfield workflow Structured Q&A → vision → constitution → specify → clarify → plan.
fact-research brownfield workflow Parallel sub-agents map the codebase → research.md → delta spec.
fact-implement implement phase Per-task discipline: read plan, apply skills, write code, mark done.
fact-tdd by fact-implement for tasks that touch business logic RED-GREEN-REFACTOR cycle. Failing test first, smallest code to pass, refactor under green.
fact-verify by fact-implement before flipping [x] on any task Verification checklist: tests pass, type-check clean, behavior matches plan, no TODOs / skipped tests left, diff matches files the plan listed.
fact-skill-installer when an external skill is needed Search skills.sh, present to user, install with explicit confirmation.
fact-audit when a hook trigger arrives Orchestrates security / architecture / quality reviews; also runs the project test suite as a separate action on session-stop / /fact-audit all.

Project layout

When FACT manages a project:

my-project/
├── .claude/
│   ├── skills/
│   │   ├── fact-*/SKILL.md                  (FACT base skills, listed above)
│   │   └── speckit-*/SKILL.md               (Spec Kit's own skills)
│   ├── commands/
│   │   ├── fact-start.md
│   │   ├── fact-next.md
│   │   ├── fact-status.md
│   │   └── fact-audit.md
│   ├── hooks/                               (pure-Python — Claude Code calls them directly)
│   │   ├── fact_hook.py                     (FACT observation; tool/session/subagent events)
│   │   ├── fact_audit.py                    (per-file audit trigger on PostToolUse)
│   │   ├── fact_audit_stop.py               (session-stop audit + test-suite runner helper)
│   │   ├── fact_compact_progress.py         (60% context-window compaction trigger)
│   │   ├── fact_compact.py                  (compaction helper, invoked on demand)
│   │   └── fact_session_resume.py           (resume nudge on SessionStart)
│   └── settings.json                        (hook wiring)
├── .specify/
│   ├── memory/
│   │   └── constitution.md                  (Spec Kit)
│   ├── specs/
│   │   └── <NNN-feature>/                   (Spec Kit per-feature)
│   │       ├── spec.md, plan.md, tasks.md, research.md
│   │       ├── checklists/, contracts/, …
│   └── fact/                                (FACT operational state)
│       ├── config.json                      (port, host, agent type)
│       ├── dashboard.pid                    (running dashboard pid)
│       ├── events.jsonl                     (append-only hook log)
│       ├── session_state.json               (mechanical state)
│       ├── sessions/<UTC>.md                (semantic summaries)
│       ├── audits/<UTC>-<dim>.md            (audit reports)
│       └── .stop-audit-<id>.fired           (loop guard markers)
├── CLAUDE.md                                (~20 lines, points at skills)
└── (your code: src/, tests/, etc)

Key principle: everything FACT writes lives under .specify/fact/. There is no parallel ~/.fact/ or ./fact/ directory in the project. If you rm -rf .specify/, you reset both Spec Kit AND FACT — clean slate.


Continuity

FACT persists state continuously, not at session-close. If you Ctrl+C Claude or the process crashes, the latest snapshot is already on disk. On reopen:

  1. fact-onboarding reads session_state.json for mechanical state (active task, recent files, model, last update).
  2. It reads the latest sessions/<UTC>.md summary for semantic state (decisions, what was tried, what's next).
  3. It presents a continuity message and asks if you want to continue from where you were.

Three resumption cases handled by the skill:

  • Clean close — last task was marked [x]. Asks: continue with the next pending task?
  • Mid-task abandon — last task was [ ] but files were modified. Asks: pick up where I left, or reset and start over?
  • Corrupt statesession_state.json missing/garbled. Falls back to the Spec Kit files alone, asks the user what to do.

If both layers are gone (rm -rf .specify/fact/), FACT degrades to Spec Kit-only — exactly how Spec Kit projects work without FACT.


Configuration

Dashboard port

Default: 7842. Override at init time:

fact init --port 7900

Or edit .specify/fact/config.json:

{
  "version": "0.1.0",
  "agent": "claude-code",
  "dashboard": { "host": "127.0.0.1", "port": 7842 }
}

Pricing

Token costs come from pricing.json shipped with FACT. Verify against Anthropic's pricing page at release time; update via fact upgrade when models change.

Hooks

.claude/settings.json is managed by fact init / fact upgrade. Don't hand-edit unless you know what you're doing — re-running fact upgrade will preserve your additions but might add FACT entries again if the markers change.


Troubleshooting

Problem Fix
Dashboard shows nothing — empty kanban The agent hasn't run /speckit.tasks yet. Phase cards still appear; T-NNN cards arrive when tasks.md is generated.
Dashboard isn't reflecting changes Hard refresh the browser (Cmd+Shift+R). Cache headers should prevent this but a stale tab can stick.
specify not found / install failed Run fact doctor --fix. If still failing, install manually with uv tool install --from git+https://github.com/github/spec-kit.git specify-cli.
🔒 FACT AUDIT keeps re-firing on Stop Update FACT (fact upgrade). The Stop hook now fires at most once per session.
Cost shows $0.00 despite agent activity The dashboard reads tokens from the Claude Code transcript. Make sure the project was init'd with fact init; then fact upgrade to refresh hook helpers.
Agent forgot to write active_task_id The dashboard infers in-progress from the recent file edit buffer. Should self-correct after the next file edit.
fact upgrade says nothing changed That's fine — it's idempotent. To force a refresh, delete .claude/skills/fact-* and re-run.
I want to restart from scratch fact stop && rm -rf .specify .claude/skills/fact-* .claude/commands/fact-* .claude/hooks && fact init. Your code is untouched.
Windows: pipx install ... fails with Unable to create process using ...python.exe The pipx shim is hard-coded to a Python that no longer exists at that path. Either reinstall pipx (python -m pip install --user --upgrade pipx) or switch to uv (recommended on Windows).
Hooks don't fire / dashboard stays empty Hook commands in .claude/settings.json reference an absolute path to the Python interpreter that ran fact init. If that interpreter has since moved or been uninstalled, the hooks silently fail. Re-run fact upgrade to refresh the paths.
Claude Code shows Unknown hook event "SubagentEnd" Old FACT version. Run fact upgrade inside the project — it renames the event to SubagentStop (Claude Code's current name) and removes the stale entry from settings.json.

Design principles

These guide every implementation decision in FACT. If a change violates one, the change is wrong, not the principle.

  1. Single source of truth: Spec Kit .md files. FACT never writes parallel state files as a substitute. Every derived view (dashboard, status command) reads from the Spec Kit files.
  2. The agent never spends tokens maintaining FACT metadata. What FACT needs to know is deduced from hooks, the filesystem, and the files Spec Kit already generates. Semantic summaries the agent writes are the same it would write under good RPI practice.
  3. CLAUDE.md is 20 lines or less. Detailed rules live in skills, loaded on demand.
  4. RPI rules are non-negotiable. The 40% smart-zone, intentional compaction, sub-agents for forking context, code snippets in plans — these aren't bendable.
  5. Sub-agents fork context, not roles. No "frontend agent" or "backend agent". Sub-agents are a compression mechanism.
  6. Sub-agents use differentiated models. Haiku for lookup, Sonnet for synthesis, the main model for deep reasoning.
  7. External skills require explicit user confirmation. The agent never downloads a skill without a clear "yes" in chat.
  8. FACT runs alongside, never in the middle. No wrapping, no proxying.
  9. Cheap extensibility, not expensive. A single Protocol (AgentAdapter), one concrete impl. No plugin registry.
  10. Honest metrics. If a number can't be computed accurately, show a placeholder, never fabricate.
  11. One project folder. Everything FACT writes is under .specify/fact/. No parallel root directories.
  12. Continuity is automatic. The user never runs a pause or save ritual. Close anytime, reopen, the agent catches up.

License

MIT.

Project details


Download files

Download the file for your platform. If you're not sure which to choose, learn more about installing packages.

Source Distribution

fact_toolkit-0.3.2.tar.gz (273.9 kB view details)

Uploaded Source

Built Distribution

If you're not sure about the file name format, learn more about wheel file names.

fact_toolkit-0.3.2-py3-none-any.whl (112.1 kB view details)

Uploaded Python 3

File details

Details for the file fact_toolkit-0.3.2.tar.gz.

File metadata

  • Download URL: fact_toolkit-0.3.2.tar.gz
  • Upload date:
  • Size: 273.9 kB
  • Tags: Source
  • Uploaded using Trusted Publishing? Yes
  • Uploaded via: twine/6.1.0 CPython/3.13.12

File hashes

Hashes for fact_toolkit-0.3.2.tar.gz
Algorithm Hash digest
SHA256 5fb85ee236459a2fb62920665393f137454d94021d040f8f6bd7e3154d3c9343
MD5 a716df430c82d96e602eb78403953f1d
BLAKE2b-256 f87fb56fd4aeb879299006e2962ae99b25b3945dcaae74d9d0c13a8c45467b09

See more details on using hashes here.

Provenance

The following attestation bundles were made for fact_toolkit-0.3.2.tar.gz:

Publisher: release.yml on holaPymbu/fact

Attestations: Values shown here reflect the state when the release was signed and may no longer be current.

File details

Details for the file fact_toolkit-0.3.2-py3-none-any.whl.

File metadata

  • Download URL: fact_toolkit-0.3.2-py3-none-any.whl
  • Upload date:
  • Size: 112.1 kB
  • Tags: Python 3
  • Uploaded using Trusted Publishing? Yes
  • Uploaded via: twine/6.1.0 CPython/3.13.12

File hashes

Hashes for fact_toolkit-0.3.2-py3-none-any.whl
Algorithm Hash digest
SHA256 c72ed135def4188dc3b503ea72251111b9ce756c91b257179cd4c8961aa0658b
MD5 f9018b2864d61cde467417e8f42ac920
BLAKE2b-256 f6befaf3893a6e4005cb4d225f12570217a049ee2590729f6a9a9e34177f39f3

See more details on using hashes here.

Provenance

The following attestation bundles were made for fact_toolkit-0.3.2-py3-none-any.whl:

Publisher: release.yml on holaPymbu/fact

Attestations: Values shown here reflect the state when the release was signed and may no longer be current.

Supported by

AWS Cloud computing and Security Sponsor Datadog Monitoring Depot Continuous Integration Fastly CDN Google Download Analytics Pingdom Monitoring Sentry Error logging StatusPage Status page