fapony 0.1.2 → 0.1.3
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +22 -36
- package/images/logo.png +0 -0
- package/images/logo.webp +0 -0
- package/images/logo@400.webp +0 -0
- package/images/sample.webp +0 -0
- package/images/summary.webp +0 -0
- package/package.json +3 -2
- package/src/mcp/transport.ts +1 -1
package/README.md
CHANGED
|
@@ -4,6 +4,8 @@
|
|
|
4
4
|
|
|
5
5
|
# fapony
|
|
6
6
|
|
|
7
|
+
[](https://www.npmjs.com/package/fapony)
|
|
8
|
+
|
|
7
9
|
**Where did your tokens go?** fapony reads the session logs Claude Code, Codex, OpenCode and ZCode
|
|
8
10
|
already write, and puts them all on one yardstick — tokens, cost and time per model, per client,
|
|
9
11
|
per workflow. Nothing to instrument, no per-project setup, no waiting for data to accumulate: it
|
|
@@ -41,8 +43,8 @@ which kind of task" becomes a data question instead of a vibe. On top of measure
|
|
|
41
43
|
claims against git facts: handoff conformance, allowlisted evidence, a 6-grade verdict — with
|
|
42
44
|
everything the agent claimed but couldn't prove marked as such.
|
|
43
45
|
|
|
44
|
-
**What that question looks like answered, from one project's own ledger
|
|
45
|
-
|
|
46
|
+
**What that question looks like answered, from one project's own ledger — the top of the `n≥5`
|
|
47
|
+
frontier (`fapony stats --mode verdict --regime code`):**
|
|
46
48
|
|
|
47
49
|
| model | tokens/pass | quality | n |
|
|
48
50
|
|---|---|---|---|
|
|
@@ -56,7 +58,7 @@ on you to hold: work isn't randomly assigned to models, so a gap this size is a
|
|
|
56
58
|
controlled trial — you likely route easy tasks to the cheap model already. `n≥5` is fapony's own
|
|
57
59
|
floor before a model counts toward the frontier at all; below that it's a data point, not a pick.
|
|
58
60
|
|
|
59
|
-
**The reason to keep it running is the third layer: knowledge accumulation.** Any single client already logs its own session — timing, tokens, tool calls. What none of them see is *across* runs, clients and task shapes: which model earns its keep on which kind of work **in this project**, at what token cost, graded by whoever reviewed it. Every verdict carries a `regime` (`code` / `fix` / `review` / `plan` / `inquiry` / `test`), and runs split by whether there was a plan at all — so "does planning beat diving in, and for which model" is a table, not an argument.
|
|
61
|
+
**The reason to keep it running is the third layer: knowledge accumulation.** Any single client already logs its own session — timing, tokens, tool calls. What none of them see is *across* runs, clients and task shapes: which model earns its keep on which kind of work **in this project**, at what token cost, graded by whoever reviewed it. Every verdict carries a `regime` (`code` / `fix` / `review` / `plan` / `inquiry` / `test`), and runs split by whether there was a plan at all — so "does planning beat diving in, and for which model" is a table, not an argument.
|
|
60
62
|
|
|
61
63
|
Three tiers, deliberately: **measurement ships today** and needs no per-project setup — raw facts nobody can call unfair. **Verification is the sharper edge** but stays beta until its evidence layer is hardened; fapony doesn't control your agent's flow, so it never promises "verified" as a headline. **Knowledge accumulation is the compounding one** — it's worthless on run 1 and gets more useful every run after, which is exactly why it's the layer competitors can't clone by copying a feature list.
|
|
62
64
|
|
|
@@ -67,8 +69,7 @@ Adopting it doesn't change your workflow. There is no loop to join and no framew
|
|
|
67
69
|
Stated up front, because the gap between these two things is where most tooling oversells:
|
|
68
70
|
|
|
69
71
|
- **It does not run your test suite.** The evidence collector runs an allowlist *you* write in
|
|
70
|
-
`.fapony/evidence.json`, and never a command an agent proposes. No allowlist, no evidence
|
|
71
|
-
the report says `not_run` rather than staying quiet.
|
|
72
|
+
`.fapony/evidence.json`, and never a command an agent proposes. No allowlist, no evidence.
|
|
72
73
|
- **It does not judge your code.** `verdict_submit` *stores* a verdict; a human or a reviewing
|
|
73
74
|
agent supplies it. fapony is the ledger, not the judge.
|
|
74
75
|
- **`handoff_check` checks conformance, not correctness.** It verifies that what the agent claimed
|
|
@@ -81,15 +82,15 @@ Stated up front, because the gap between these two things is where most tooling
|
|
|
81
82
|
reviews and files the verdict, the grade lands on the reviewer. Reports label it `inferred`;
|
|
82
83
|
read it as such.
|
|
83
84
|
- **The knowledge layer is empty on run 1.** It is worth something around run 5 and more every run
|
|
84
|
-
after.
|
|
85
|
+
after.
|
|
85
86
|
|
|
86
87
|
## Quick start (MCP)
|
|
87
88
|
|
|
88
89
|
```bash
|
|
89
90
|
# 1. Install (needs Bun — https://bun.sh)
|
|
90
|
-
|
|
91
|
-
|
|
92
|
-
|
|
91
|
+
npm install -g fapony # or: bun add -g fapony
|
|
92
|
+
# from source instead:
|
|
93
|
+
# git clone https://github.com/kire21b/fapony.git && cd fapony && bun install && bun link
|
|
93
94
|
# note: `bun link` claims the global `fapony` bin by package name, not path — running it
|
|
94
95
|
# from a second checkout silently repoints the command there. Re-run it in the one you want.
|
|
95
96
|
|
|
@@ -112,14 +113,7 @@ fapony usage-web # dashboard; re-run the scans to refre
|
|
|
112
113
|
|
|
113
114
|
# 4. Verify (optional, per project) — scaffold the evidence allowlist
|
|
114
115
|
fapony init /path/to/your-worktree
|
|
115
|
-
# .fapony/evidence.json
|
|
116
|
-
# edit the placeholder cmds to your real test/typecheck commands
|
|
117
|
-
# commit it: the allowlist is a security boundary your whole team shares.
|
|
118
|
-
# If your .gitignore ignores .fapony/ wholesale, re-include it (dir before file):
|
|
119
|
-
# **/.fapony/*
|
|
120
|
-
# !**/.fapony/evidence.json
|
|
121
|
-
# Monorepo: give an app its own apps/<app>/.fapony/evidence.json and reports whose
|
|
122
|
-
# changed files all sit under that app use it; anything else uses the root one.
|
|
116
|
+
# edit .fapony/evidence.json to your real test/typecheck commands, then commit it
|
|
123
117
|
```
|
|
124
118
|
|
|
125
119
|
With `.fapony/evidence.json` in place, any graded run can be replayed as a report. This one is
|
|
@@ -135,6 +129,8 @@ You get one report: git facts (files, commits, branch), handoff conformance (cla
|
|
|
135
129
|
|
|
136
130
|
Sections that have nothing to report say so (`not_run`, `unavailable`) rather than disappearing — a report with no evidence must not read like a report that passed.
|
|
137
131
|
|
|
132
|
+
Two details for the allowlist once it is under version control. If your `.gitignore` ignores `.fapony/` wholesale, re-include the file (dir before file): `**/.fapony/*`, then `!**/.fapony/evidence.json`. In a monorepo, give an app its own `apps/<app>/.fapony/evidence.json` — reports whose changed files all sit under that app use it; anything else uses the root one.
|
|
133
|
+
|
|
138
134
|
Two things worth knowing about the report header and budget:
|
|
139
135
|
|
|
140
136
|
- **`server_sha`** — every report is stamped with the git SHA of the fapony code that produced it, read once at server start. MCP servers are long-lived: after you edit fapony and don't restart the client, reports keep coming from the old build. Compare the stamp against `git log -1` in the fapony repo; if they differ, reconnect the server before trusting the result.
|
|
@@ -199,14 +195,6 @@ ungraded. It never picks the grade; it cannot see whether the work held up.
|
|
|
199
195
|
|
|
200
196
|
### The 6 tools
|
|
201
197
|
|
|
202
|
-
```
|
|
203
|
-
discover: plan_list (plans grouped by state, joined with their run history)
|
|
204
|
-
measure: fapony_stats ── fapony_usage
|
|
205
|
-
verify: verdict_submit
|
|
206
|
-
recall: project_health_context (what failed in these files before — optional, never required)
|
|
207
|
-
mem_find (what was ever decided about these files — reads the project's mem log)
|
|
208
|
-
```
|
|
209
|
-
|
|
210
198
|
| Tool | Tier | Purpose |
|
|
211
199
|
|------|------|---------|
|
|
212
200
|
| `plan_list` | discover | Plan files grouped by state — active / blocked / untouched / superseded / trackers — with a progress tally and each one's run history. Not a raw `ls`; see [Plans your agent can answer questions about](#plans-your-agent-can-answer-questions-about) |
|
|
@@ -218,7 +206,7 @@ recall: project_health_context (what failed in these files before — optional
|
|
|
218
206
|
|
|
219
207
|
The handoff/report family is CLI-only — the schemas cost every session of every client and no skill called them. `fapony report <run-id>` prints the full report for a run (facts + handoff conformance + evidence + verdict); `fapony report-web [file]` renders it as a static HTML page (overwrites `file` on every call — safe to reuse the same path). Run `bun run overview` for a one-shot shortcut that writes it to `/tmp/fapony-overview.html` and opens it. `fapony usage-scan` scans session logs and writes a cache file; `fapony usage-web [port]` serves a static HTML dashboard from that cache (no live scanning). Run `fapony usage-scan` periodically to keep data fresh.
|
|
220
208
|
|
|
221
|
-
Full protocol, adapter examples (bash, Python), and safety rules: [docs/mcp-handcheck.md](docs/mcp-handcheck.md).
|
|
209
|
+
Full protocol, adapter examples (bash, Python), and safety rules: [docs/mcp-handcheck.md](https://github.com/kire21b/fapony/blob/main/docs/mcp-handcheck.md).
|
|
222
210
|
|
|
223
211
|
### Verdict grades
|
|
224
212
|
|
|
@@ -304,9 +292,7 @@ flowchart TD
|
|
|
304
292
|
**The fork at the top is load-bearing.** A plan file is an artifact for work the next session has
|
|
305
293
|
to pick up. Wiring, refactors and UI passes finish in one sitting and the PLAN.md gets archived
|
|
306
294
|
unread — so `/plan-with-pony` declines those itself and hands over the two seed commands instead.
|
|
307
|
-
|
|
308
|
-
here, who imports it, what is untested" for about a thirtieth of the tokens reading those files
|
|
309
|
-
costs. Both arms meet at the same review and the same ledger.
|
|
295
|
+
Both arms meet at the same review and the same ledger.
|
|
310
296
|
|
|
311
297
|
**The dotted edges are the whole point.** Verdicts carry `regime` and `reason_code`, so the
|
|
312
298
|
ledger can answer the one question no single client can: *in this project, which model is worth
|
|
@@ -345,7 +331,7 @@ cat skill/plan-with-pony/SKILL.md | opencode run # OpenCode
|
|
|
345
331
|
cat skill/plan-with-pony/SKILL.md | <your-agent> # anything that reads stdin
|
|
346
332
|
```
|
|
347
333
|
|
|
348
|
-
Example plans produced by it live in [examples/](examples
|
|
334
|
+
Example plans produced by it live in [examples/](https://github.com/kire21b/fapony/tree/main/examples).
|
|
349
335
|
|
|
350
336
|
### Plans your agent can answer questions about
|
|
351
337
|
|
|
@@ -404,7 +390,7 @@ The layout, and why archiving is a plain `git mv`:
|
|
|
404
390
|
Ship dates live in the plan's own header (`> ✅ **shipped 2026-09-13** (a1b2c3)`), not in the
|
|
405
391
|
filename — `grep -h shipped .fapony/done/*.md | sort` answers "what landed when" without paying
|
|
406
392
|
to rewrite every inbound link on every ship. Example plans, including an un-annotated one and an
|
|
407
|
-
archived one: [examples/](examples
|
|
393
|
+
archived one: [examples/](https://github.com/kire21b/fapony/tree/main/examples).
|
|
408
394
|
|
|
409
395
|
## CLI
|
|
410
396
|
|
|
@@ -430,13 +416,13 @@ fapony install --platform <name> # force a specific client (bypasses de
|
|
|
430
416
|
fapony install --dry-run # show what would happen without writing files
|
|
431
417
|
fapony setup # interactive wizard: config + scaffold in one step
|
|
432
418
|
fapony update # self-update via git pull
|
|
433
|
-
fapony telemetry show|send # opt-in only, default off — see TELEMETRY.md
|
|
419
|
+
fapony telemetry show|send # opt-in only, default off — see https://github.com/kire21b/fapony/blob/main/TELEMETRY.md
|
|
434
420
|
fapony test # self-check
|
|
435
421
|
```
|
|
436
422
|
|
|
437
423
|
## Config
|
|
438
424
|
|
|
439
|
-
`fapony.config.json` lives in the fapony checkout and is gitignored (it's per-machine). Copy [fapony.config.example.json](fapony.config.example.json) for a complete working reference; every section is optional with sane defaults. Key fields:
|
|
425
|
+
`fapony.config.json` lives in the fapony checkout and is gitignored (it's per-machine). Copy [fapony.config.example.json](https://github.com/kire21b/fapony/blob/main/fapony.config.example.json) for a complete working reference; every section is optional with sane defaults. Key fields:
|
|
440
426
|
|
|
441
427
|
- `worktrees` — name → absolute path mapping
|
|
442
428
|
- `review.maxRounds` — round cap enforced by the gate
|
|
@@ -444,7 +430,7 @@ fapony test # self-check
|
|
|
444
430
|
- `paths` (`planDir`/`doneDir`/`specDir`/`memoryEntry`/`stateDir`) / `safety` — directory layout and the dangerous-command deny-list
|
|
445
431
|
- `usageWeb` — optional `{ port, hostname }` for `fapony usage-web` server defaults. Run `fapony usage-scan` first to populate the cache.
|
|
446
432
|
|
|
447
|
-
Env overrides: `FAPONY_CONFIG` (config file), `FAPONY_STATE_DIR` (state DB location; default `~/.config/fapony/`). Full schema, design decisions, and edge cases
|
|
433
|
+
Env overrides: `FAPONY_CONFIG` (config file), `FAPONY_STATE_DIR` (state DB location; default `~/.config/fapony/`). Full schema, design decisions, and edge cases live with the code in the repo — this README intentionally doesn't duplicate them.
|
|
448
434
|
|
|
449
435
|
## Scope
|
|
450
436
|
|
|
@@ -453,10 +439,10 @@ Env overrides: `FAPONY_CONFIG` (config file), `FAPONY_STATE_DIR` (state DB locat
|
|
|
453
439
|
- Measurement: cross-run KPIs by model/grade/value, per-file risk (graded touches vs. fails) + passive usage (tokens, cost)
|
|
454
440
|
- Model attribution across clients — resolved from the session log that was live when the verdict landed, so a verdict carries a model without the caller declaring one
|
|
455
441
|
- Zero setup beyond install: the two habits fapony depends on ship in the MCP `initialize` response, not in your rules file
|
|
456
|
-
- Verification (beta): handoff conformance, 6-grade verdicts, allowlisted evidence collector (`.fapony/evidence.json`
|
|
442
|
+
- Verification (beta): handoff conformance, 6-grade verdicts, allowlisted evidence collector (`.fapony/evidence.json`); reports stamped with the producing build's `server_sha`
|
|
457
443
|
- Vendor-neutral executor/reviewer roles — anything that reads stdin
|
|
458
444
|
- Memory integration via shell adapter, per project (configurable or default-wired)
|
|
459
|
-
- Opt-in telemetry, off by default ([TELEMETRY.md](TELEMETRY.md) lists exactly what leaves the machine)
|
|
445
|
+
- Opt-in telemetry, off by default ([TELEMETRY.md](https://github.com/kire21b/fapony/blob/main/TELEMETRY.md) lists exactly what leaves the machine)
|
|
460
446
|
- Bun-only; run state in SQLite via `bun:sqlite` (WAL mode)
|
|
461
447
|
|
|
462
448
|
**Not supported (yet):**
|
package/images/logo.png
ADDED
|
Binary file
|
package/images/logo.webp
ADDED
|
Binary file
|
|
Binary file
|
|
Binary file
|
|
Binary file
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "fapony",
|
|
3
|
-
"version": "0.1.
|
|
3
|
+
"version": "0.1.3",
|
|
4
4
|
"description": "Measurement layer for coding agents — measure what agents do, verify what they claim. 6 MCP tools, any agent, no loop required",
|
|
5
5
|
"license": "MIT",
|
|
6
6
|
"author": "delamind (https://github.com/kire21b)",
|
|
@@ -24,7 +24,8 @@
|
|
|
24
24
|
"fapony.ts",
|
|
25
25
|
"src/",
|
|
26
26
|
"templates/",
|
|
27
|
-
"skill/"
|
|
27
|
+
"skill/",
|
|
28
|
+
"images/"
|
|
28
29
|
],
|
|
29
30
|
"scripts": {
|
|
30
31
|
"lint": "biome check .",
|
package/src/mcp/transport.ts
CHANGED
|
@@ -112,7 +112,7 @@ function writeStatuslineCache(toolResult: ToolResult): void {
|
|
|
112
112
|
|
|
113
113
|
const MCP_PROTOCOL_VERSION = "2025-03-26";
|
|
114
114
|
const SERVER_NAME = "fapony-handcheck";
|
|
115
|
-
const SERVER_VERSION = "0.1.
|
|
115
|
+
const SERVER_VERSION = "0.1.3";
|
|
116
116
|
|
|
117
117
|
// --- JSON-RPC dispatch ---
|
|
118
118
|
|