Install any skill in seconds. Free to start, no credit card required.
Get Started Free →How to set up a sandboxed fdeops engagement and test the fde CLI + rendered Fieldbook HTML UI end-to-end (including privacy/<private> leak checks and before/after contrast against an older build).
.claude/skills/suboss87-testing-fieldbook/SKILL.md| Test case | Without → With | Effect | Δ tokens | Δ turns |
|---|---|---|---|---|
| case-04 | ✗→✓ | ▲ Improved | -4% | 0% |
| case-06 | ✗→✓ | ▲ Improved | 26% | 0% |
| case-07 | ✗→✓ | ▲ Improved | -36% | 0% |
| case-08 | ✗→✓ | ▲ Improved | -43% | 0% |
| case-10 | ✗→✓ | ▲ Improved | 44% | 0% |
fdeops is a zero-dependency, local-only Node CLI (bin/fde.js). Nothing to install beyond Node 20. npm run check runs the invariant checker plus the unit tests.
Never write into ~/fde-engagements. Every command respects FDEOPS_ENGAGEMENTS_ROOT:
bashexport FDEOPS_ENGAGEMENTS_ROOT=/tmp/fbrun/engagements export F=/path/to/repo/bin/fde.js mkdir -p /tmp/fbrun/{engagements,ws-a,ws-b,nowhere} cd /tmp/fbrun/ws-a && node $F resume --init acme-corp # binds THIS cwd to the engagement
A workspace must be bound (resume --init) before any write command works; run each engagement's commands from its own bound scratch directory. /tmp/fbrun/nowhere stays unbound and is where you test the "NO ENGAGEMENT" path (exit code 2).
fde debrief --smart <notes-file> writes a proposal and prints the routing; fde debrief --apply commits it. Prefixed lines route deterministically:
Decided: … → decisions.mdRisk: … → risks.mdDelivered: … → delivery.mdNext: … → context.md ## Next actioncontext.md notesPlain prose naming a person does not create a stakeholder. To drive per-person trust dots and the overall trust color, use fde log contact "Name (Role) - note" --signal green|amber|red. Trust is "worst active signal wins", so one red contact makes the whole engagement render at risk. fde log phase build sets the phase badge (rendered as "Build & Guard").
bashnode $F dashboard # -> $FDEOPS_ENGAGEMENTS_ROOT/fieldbook-current.html (bound engagement only) node $F dashboard --all # -> $FDEOPS_ENGAGEMENTS_ROOT/fieldbook.html (portfolio)
Open them in Chrome as file:///tmp/fbrun/engagements/fieldbook-current.html. The page is a static render of .fde/*.md — every rendered value should be checkable against the markdown, so diff the card against grep -h '^- \[' .fde/{decisions,risks,delivery,stakeholders}.md.
fde dashboard --open shells out to xdg-open <plain path>. In Devin sandboxes ~/.local/bin/google-chrome is a harness shim that URI-encodes its argument, so a plain path becomes %2Ftmp%2F… and Chrome opens about:blank. That is an environment artifact, not a product bug — verify by navigating to the file:/// URL manually and note --open as untested.
<private> … </private> blocks in any .fde/*.md must be stripped from every model-facing read (stripPrivate/readClean in bin/fde.js). To test:
bashfor f in context risks stakeholders; do printf '\n<private>\nBank account for payout: 12345678\n</private>\n' >> $FDEOPS_ENGAGEMENTS_ROOT/<client>/.fde/$f.md done node $F dashboard && node $F dashboard --all grep -c 12345678 $FDEOPS_ENGAGEMENTS_ROOT/fieldbook*.html # expect 0 for c in "resume" "resume --full" "triage" "prep x" "status --all" "receipts" "garden" "doctor" "scan"; do printf '%-16s leaks: %s\n' "$c" "$(node $F $c 2>&1 | grep -c 12345678)" done
Always confirm the secret is present in the raw markdown first, otherwise the test passes vacuously. In Chrome check view-source:file:///… with Ctrl+F (0 matches) and also search private - redacted, which is the replacement marker.
fde redact <term> previews matching lines; --apply deletes them and commits the memory ledger. fde log --undo removes the last CLI-written log/debrief entry.
For PRs that only change CLI output, build the previous version as a worktree and run both binaries side by side in a visible terminal — this is what makes a recording convincing:
bashgit worktree add /tmp/fde-old HEAD~1 node /tmp/fde-old/bin/fde.js resume # old behavior node $F resume # new behavior
The app under test is a CLI, so run the commands in a real terminal (konsole --workdir <dir>, maximized with wmctrl -r :ACTIVE: -b add,maximized_vert,maximized_horz) and switch to Chrome for the HTML. Increase Konsole font with ctrl+shift+equal a few times before recording. Verify export lines actually took effect (echo $VAR) — the first keystrokes sent to a freshly focused Konsole window are sometimes dropped.
fde doctor exits 1 whenever it reports hygiene issues.[@…] owner tag comes from the local git email, so it renders as the devin bot.fde log contact entries appear twice in the Fieldbook LOG panel (written to bothstakeholders.md ## Signal history and .fde/.signal-ledger, read without de-duplication).
None — the CLI never reaches the network and requires no credentials.
| Case | Status | Duration (ms) | Turns | Tokens | Tool calls | ||||||||
|---|---|---|---|---|---|---|---|---|---|---|---|---|---|
| Without | With | Δ | Without | With | Δ | Without | With | Δ | Without | With | Δ | ||
case-01 | fail→fail | 30,020 | 20,443 | -32% | 1 | 1 | 0% | 3,180 | 1,861 | -41% | 0 | 0 | — |
case-02 | fail→fail | 12,900 | 14,806 | +15% | 1 | 1 | 0% | 2,316 | 1,816 | -22% | 0 | 0 | — |
case-03 | fail→fail | 21,177 | 10,219 | -52% | 1 | 1 | 0% | 3,108 | 1,701 | -45% | 0 | 0 | — |
case-04 | fail→pass | 11,600 | 2,467 | -79% | 1 | 1 | 0% | 1,825 | 1,758 | -4% | 0 | 0 | — |
case-05 | pass→pass | 8,162 | 6,892 | -16% | 1 | 1 | 0% | 1,454 | 1,673 | +15% | 0 | 0 | — |
case-06 | fail→pass | 8,960 | 7,038 | -21% | 1 | 1 | 0% | 1,407 | 1,768 | +26% | 0 | 0 | — |
case-07 | fail→pass | 22,454 | 3,756 | -83% | 1 | 1 | 0% | 3,147 | 2,014 | -36% | 0 | 0 | — |
case-08 | fail→pass | 17,362 | 7,779 | -55% | 1 | 1 | 0% | 2,863 | 1,638 | -43% | 0 | 0 | — |
case-09 | fail→fail | 18,960 | 10,146 | -46% | 1 | 1 | 0% | 2,281 | 1,793 | -21% | 0 | 0 | — |
case-10 | fail→pass | 6,737 | 7,656 | +14% | 1 | 1 | 0% | 1,268 | 1,826 | +44% | 0 | 0 | — |
case-11 | fail→pass | 11,614 | 8,031 | -31% | 1 | 1 | 0% | 1,743 | 1,990 | +14% | 0 | 0 | — |
case-12 | fail→pass | 9,923 | 6,773 | -32% | 1 | 1 | 0% | 1,075 | 1,613 | +50% | 0 | 0 | — |
case-13 | fail→pass | 16,667 | 2,195 | -87% | 1 | 1 | 0% | 1,970 | 1,724 | -12% | 0 | 0 | — |
case-14 | fail→fail | 9,898 | 2,774 | -72% | 1 | 1 | 0% | 1,496 | 1,786 | +19% | 0 | 0 | — |
case-15 | pass→pass | 16,613 | 12,171 | -27% | 1 | 1 | 0% | 1,782 | 2,142 | +20% | 0 | 0 | — |
case-16 | pass→fail | 15,649 | 10,656 | -32% | 1 | 1 | 0% | 1,644 | 1,623 | -1% | 0 | 0 | — |
case-17 | fail→fail | 12,897 | 5,687 | -56% | 1 | 1 | 0% | 2,198 | 1,669 | -24% | 0 | 0 | — |
case-18 | fail→pass | 7,897 | 2,563 | -68% | 1 | 1 | 0% | 1,335 | 1,835 | +37% | 0 | 0 | — |
case-19 | fail→pass | 7,414 | 1,531 | -79% | 1 | 1 | 0% | 1,361 | 1,633 | +20% | 0 | 0 | — |
case-20 | fail→fail | 12,305 | 5,102 | -59% | 1 | 1 | 0% | 2,191 | 1,593 | -27% | 0 | 0 | — |
case-21 | fail→fail | 14,125 | 5,805 | -59% | 1 | 1 | 0% | 2,605 | 1,607 | -38% | 0 | 0 | — |
case-22 | fail→pass | 19,150 | 10,443 | -45% | 1 | 1 | 0% | 3,457 | 2,577 | -25% | 0 | 0 | — |
DecimalAI ran this skill against gemini-3.6-flash twice over the same eval suite — once with the skill loaded and once without — and compared the two runs case by case. 22 cases were attempted, and 15 counted toward the lift figure. The other 7 produced results that are not comparable between the two arms, so they are excluded from the headline rather than averaged into it. The headline lift of +45 percentage points is the difference between those two pass rates over the 15 comparable cases. 1 case got worse with the skill loaded, and it is included in that figure.
Without the skill loaded, the model failed this case. With it loaded, the same prompt on the same model passed. This is one improved case from the latest verified run; every case, including any that regressed, is in the table above.
Other measured skills in the registry, with their headline benchmark lift.