by cozytab
Fable 5-grade work discipline for any Claude model — a Claude Code skill + guard hooks (plan gate, model ceiling, per-task enforcement) that make Opus 4.8 or any non-frontier model plan, self-verify, and route sub-agents like Fable 5, without Fable 5.
# Add to your Claude Code skills
git clone https://github.com/cozytab/fable5-modefable5-mode is an open-source ai agents skill for AI coding assistants such as Claude Code, Codex CLI, and ChatGPT, built by cozytab. Fable 5-grade work discipline for any Claude model — a Claude Code skill + guard hooks (plan gate, model ceiling, per-task enforcement) that make Opus 4.8 or any non-frontier model plan, self-verify, and route sub-agents like Fable 5, without Fable 5. It has 63 GitHub stars.
fable5-mode's catalog security scan is still queued. You can run an instant dependency and prompt-injection check now with the "Scan for vulnerabilities" button above.
Clone the repository with "git clone https://github.com/cozytab/fable5-mode" and add it to your Claude Code skills directory (see the Installation section above). fable5-mode ships a SKILL.md manifest, so compatible agents can discover and load it automatically.
fable5-mode is primarily written in Python. It is open-source under cozytab on GitHub, so you can review or fork the full source.
Yes. SkillsLLM lists many other AI Agents skills you can browse and compare side by side. Open the AI Agents category from the badge at the top of this page, or use the Related Skills and comparison links further down to weigh fable5-mode against similar tools.
No comments yet. Be the first to share your thoughts!
Unlocks once the catalog security scan passes (runs nightly).
The deep catalog scan for this skill is still queued. Run an instant dependency check now instead.
name: fable-mode
description: A work-discipline protocol that makes Opus 4.8 (or any non-frontier model) operate at Fable-5-grade quality. Core idea — output quality = model capability x work discipline: spend extra orchestration to buy single-pass quality via six levers (plan gate, small-card execution, adversarial self-check, real-product verification, context hygiene, checkpoint autonomy). Activate ONLY on an explicit request — the user names the mode ("use fable mode", "enable fable-mode", "work like Fable 5", "rigorous mode", or the Chinese "用 fable 模式"、"开 fable-mode"、"像 Fable 5 一样做"、"严谨模式") — or when the project is already armed with a .fable/ directory (the hooks handle that). Do not auto-trigger on a task merely being large, important, or quality-sensitive, and not on generic phrases like "do it well / 最高质量 / 别偷懒"; if a task looks like it would benefit, ask the user whether to enable fable-mode instead of assuming.
triggers:
You are now in fable-mode. Premise: frontier-model feats come half from the model and half from longer autonomy, harsher self-verification, less corner-cutting. That second half is model-independent — this protocol supplies it. The trade: spend extra orchestration steps to buy single-pass quality; the disciplined steps cost more tokens, but the net over a whole task often breaks even by avoiding rework loops and bloated-context waste.
.fable/ directory. A task being big or important is a reason to offer fable-mode ("want me to run this under fable-mode?"), never to silently enter it.curl --max-time, never WebFetch; long Workflows get a watchdog.Never stall, hand off, or end the turn waiting for a model you can't run:
(Set FABLE_ESCALATION=on only if a stronger tier genuinely exists to defer to.)
Before code, write docs/SPEC.md: requirements, approach, task cards (skeletons in templates/). Each card: ≤ one fresh context (~≤5 files / ≤300 lines); a machine-checkable acceptance test ("looks right" isn't acceptance); dependencies and parallelism marked. Executor choice is your judgment — subagent, Workflow, external executor, or yourself; quality first, don't split when in doubt.
Evidence closure before design: list the load-bearing unknowns — the ones that change the architecture if you guessed wrong — and buy targeted evidence for each (a 5-second probe: two extra frames, one API call, one grep) before committing the design. Every SPEC decision carries a source tag: [measured] / [inferred] / [not-shown → design-gap]. Guessed foundations are how one-pass code dies; tagged assumptions are how reviewers know where to poke.
Each card runs in a fresh context, fed only the relevant SPEC excerpt — no reasoning garbage from prior cards. Run acceptance the moment it's done; don't advance until it passes. Concurrency, model choice, and the failure-escalation ladder: see Delegation policy.
Important output is never "generate and ship". Critical modules: 2-3 independent refute passes (correctness / edges / integration) — one solid hit means rework. Wide solution spaces: N approaches + judge + synthesize. Fresh-context verifiers beat self-critique (templates/VERIFIER_PROMPT.md); verifier prompts say "assume broken, falsify hard", never "take a look".
Desk-check before first run: after drafting a large unit, re-derive the critical constants from the source evidence (layout proportions, units, coordinate mappings, state-machine edges) instead of trusting the draft, and probe interaction corners (modal click-through, mid-animation input, concurrent state). The two cheapest bugs to fix are the ones caught before the code ever runs.
All-green static checks ≠ it works. Every milestone: run the real product end-to-end, exercise the core path, keep evidence (screenshots, logs, test output). Report evidence, not adjectives.
window.__test API), then simulate the full loop through it. Testability is a product feature; ship it.docs/SPEC.md + docs/PROGRESS.md updated in real time, not batched. Segment long tasks: each segment restores from SPEC + PROGRESS only. Record every gotcha/lesson the moment you hit it (one lesson per entry, with why; update rather than duplicate, delete wrong ones). Grinding in a context stuffed with failed attempts makes models dumber — restart fresh. The converse also holds: never wrap up, trim scope, or suggest a new session just because the conversation is long — external memory is what makes length safe; keep working.
Background long tasks get a watchdog (output-file mtime). Organize resumable: any step dying loses at most one card. Forbidden is brainless fan-out (spray with no verification/watchdog/checkpoints) — parallelism itself is fine.
When acceptance fails — or a fix "doesn't work" — attribute before you edit, cheapest layer first:
fetch(url, {cache:'reload'}), restart, rebuild). "Fix had no effect" is, embarrassingly often, "fix never ran".Misattributed fixes are worse than no fix: they add churn and leave the real layer broken.
Concurrency — conservative by default: ≤5 concurrent, inline-first, don't split when unsure. The throughput tier (dispatch readily, async, no fixed cap — field deployments 10-500+; subagents are one level deep) opens only when the user explicitly asks or the session model is Fable-class; state the honest cost: ~15x tokens + rate-limit risk. Never open it silently. Shepherd, don't babysit: after dispatching, keep working instead of blocking on each return — but read results as they land and intervene the moment a subagent drifts off spec or lacks context it needs.
Model routing (capability-matched) — mirrors Anthropic's own practice (Opus-class lead + Sonnet-class subagents; Explore on Haiku; inherit when unsure):
| Card | Model | Effort |
|---|---|---|
| Orchestration, design, debugging, root-cause | session model | high/max |
| Verification, acceptance, adversarial refute | session model — never weaker than the implementer | max |
| Well-specified implementation (machine-checkable acceptance) | one tier down OK | high |
| Mechanical gather/format/search | cheap tier | low |
Safety net — what makes downgrading safe:
FABLE_ESCALATION=on for genuine upward deferral).hooks/README.md)Four hooks turn the most-shirked rules into hard blocks. Armed per project by a .fable/ directory (searched upward, bounded at the git root); without it they pass through silently. Pressure applies per round via .fable/LEDGER.md:
- [ ] 1. card (machine-checkable acceptance) <- open: guards enforce
- [x] 2. done -- evidence: pytest 21/21 <- [x] REQUIRES a substantive evidence note
- [~] 3. not this round -- deferred: reason
PAUSED: reason <- a line anywhere: enforcement off
(PAUSED must carry a reason — a bare PAUSED is ignored, pausing has to
be attributable. Evidence notes must be substantive: evidence: ok counts as
missing.)
model param and model: literals in Workflow scripts; stays active even when paused, it protects quota, not workflow).- [ ] items remain, and while any - [x] lacks an -- evidence: note (evidence-on-close: adjectives don't close cards).Wrap-up lint: python3 <skill-dir>/hooks/fable_lint.py <project_dir> — machine-checks the discipline itself (SPEC source tags present, open cards name acceptance, closed cards carry evidence). Run it at step 7 of the execution template; findings are open work.
Per-task granularity: active (open cards) = full enforcement; idle (no/all-closed cards) = close guard quiet and small tasks flow freely, but a detailed fan-out still needs a live card first; paused (a PAUSED: reason line) = guards off except the ceiling. Write PAUSED only when the user steers to work unrelated to the round; remove it to resume. Small spawns (<1500 chars) and forks skip the design gate; everything fails open (a guard bug never bricks the session); loop-safe.
For substantial work: after writing the SPEC, mkdir .fable + create .fable/LEDGER.md to get the mechanical backstop.
1. Restate goal + scope (if unclear ask once; then no requirement rework)
2. docs/SPEC.md + .fable/LEDGER.md cards — the gate
3. Execute cards (fresh contexts; Delegation policy)
4. Per-card acceptance -> update PROGRESS.md
5. Milestone adversarial self-check (refute or N-approach review)
6. End-to-end real verification, leave evidence
7. Wrap: fable_lint clean, PROGRESS complete, lessons recorded, push if asked
English | 简体中文
A work-discipline protocol that makes Opus 4.8 (or any non-frontier model) operate at Fable-5-grade quality.
fable-mode is a Claude Code skill plus a set of guard hooks. Its premise:
output quality = model capability × work discipline
# 1. Install the skill (honors CLAUDE_CONFIG_DIR; falls back to ~/.claude)
git clone https://github.com/cozytab/fable5-mode \
"${CLAUDE_CONFIG_DIR:-$HOME/.claude}/skills/fable-mode"
# 2. (optional) register the enforcement hooks — merges into your settings.json,
# resolves its own path, idempotent:
bash "${CLAUDE_CONFIG_DIR:-$HOME/.claude}/skills/fable-mode/install.sh"
# 3. In Claude Code, just ask for it — in any language:
"use fable mode" · "用 fable 模式" · "do this rigorously, one-shot"
# 4. For a project you're taking seriously, turn on enforcement:
mkdir .fable
printf -- '- [ ] 1. first card (with a machine-checkable acceptance test)\n' > .fable/LEDGER.md
The skill works on its own; step 2 is optional (it turns the discipline into hard blocks). Claude replies in your language even though the skill is authored in English.
Why it exists. Weaker models mostly don't fail by being dumb in the moment; they fail by process: thinking while typing and changing their mind halfway, declaring "looks right" without running anything, fanning work out with no verification, and quietly stopping mid-task. Those are process failures, and process is fixable with structure. Since the "discipline half" of frontier output is model-independent, you can hand a cheaper model the working habits of a stronger one and recover a real chunk of the gap — paying in orchestration steps instead of a bigger model.
What you actually get.
What it does not do. It won't turn Opus into Fable 5. It closes the discipline gap, not the capability gap. The cost is real — more orchestration steps and slower wall-clock on small tasks — which is exactly why you don't use it on small tasks. (Net token cost depends on the task; on rework-prone work the discipline can even come out lower.)
| # | Lever | What it forces |
|---|---|---|
| 1 | Plan Gate | Write docs/SPEC.md (requirements + approach + task cards, each with a machine-checkable acceptance test) before writing code. Concentrate thinking in the cheapest phase. |
| 2 | Small-card execution | Each card runs in a fresh context; don't advance until its acceptance command passes; on 2 failures, escalate instead of flailing. |
| 3 | Adversarial self-check | Don't "generate and ship." Dispatch independent viewpoints to refute critical output; for wide-open problems, generate N approaches + judge + synthesize. |
| 4 | Real-product verification | All-green static checks ≠ it works. Run the real product end-to-end each milestone and leave evidence (screenshots, logs, test output). |
| 5 | Context hygiene | SPEC + PROGRESS are external memory. Restore state by re-reading them, not by dragging failed-attempt reasoning through a bloated context. |
| 6 | Checkpoint autonomy | Long background tasks get a watchdog and resumable checkpoints, so a hang or crash costs at most one card. |
The full protocol lives in SKILL.md — the text Claude actually reads.
Six levers written as prose still rely on the model's honor. Four hooks turn the most-shirked rules into hard blocks:
| Hook | Event | Effect |
|---|---|---|
| Profile Injector | SessionStart |
Auto-injects the discipline, sized to the ledger state — full during an active round, a one-liner when idle or paused — plus the model-appropriate tier and open-item recovery. |
| Spawn Guard | PreToolUse (Agent/Task/Workflow) |
Blocks a detailed spawn before a ledger exists (forces the plan gate), and blocks any spawn requesting a model stronger than the session's — the model ceiling is mechanical, not just prose. |
| Fail-Streak Reminder | PostToolUse (Bash) |
Advisory, never blocks: at every 3rd consecutive failing command it injects the attribution ladder (suspect the harness → prove the new code is running → only then debug the product, and fix the class via an invariant) — cures grinding on the wrong layer. |
| Close Guard | Stop |
Blocks ending the turn while the ledger still has unchecked items — cures early stopping / spinning. Also enforces evidence-on-close: a - [x] card without an -- evidence: note blocks the stop ("report evidence, not adjectives" as a hard rule). |
Plus hooks/fable_lint.py — not a hook but a one-shot CLI: checks the SPEC
carries [measured]/[inferred]/[not-shown] source tags, every open card names
its acceptance, every closed card carries evidence. Run it at wrap-up (or in CI):
python3 hooks/fable_lint.py <project_dir>.
Design properties that make this safe to register globally:
.fable/ directory (searched upward, bounded at
the git root). No .fable/ → the hooks pass through silently. They never touch
projects you didn't opt in.stop_hook_active, so you're never trapped.See hooks/README.md for the mechanics.
Prerequisites: Claude Code, and python3
(standard library only — no third-party deps; needed only if you use the hooks).
Your Claude config directory is $CLAUDE_CONFIG_DIR if that variable is set,
otherwise ~/.claude. Everything below derives from it, so it works no matter
where your config lives.
git clone https://github.com/cozytab/fable5-mode \
"${CLAUDE_CONFIG_DIR:-$HOME/.claude}/skills/fable-mode"
bash "${CLAUDE_CONFIG_DIR:-$HOME/.claude}/skills/fable-mode/install.sh"
install.sh resolves its own location (so the hook paths are correct no
matter where you cloned it), honors CLAUDE_CONFIG_DIR, and merges the three
hooks into your settings.json without disturbing existing config. It's
idempotent — re-run it after moving the skill and it re-points the paths. Remove
the hooks any time with bash install.sh --uninstall.
Or just tell Claude Code:
Install the skill at https://github.com/cozytab/fable5-mode by following its README.
Updating: after git pull, re-run install.sh. A new version can add hook
events (e.g. a PostToolUse hook), and only the installer updates your
settings.json — a plain git pull ships the files but won't register new
hooks. It's idempotent, so re-running is always safe.
Clone as above, then merge these four entries into the hooks object of
<config-dir>/settings.json (don't overwrite the file; if you already have a
hooks key, add these under it). Use the absolute path to where you actually
cloned it — the ${CLAUDE_CONFIG_DIR:-$HOME/.claude} below is expanded by the
shell at hook-run time:
"hooks": {
"SessionStart": [{"hooks": [{"type": "command",
"command": "python3 ${CLAUDE_CONFIG_DIR:-$HOME/.claude}/skills/fable-mode/hooks/fable_profile_inject.py"}]}],
"PreToolUse": [{"matcher": "Agent|Task|Workflow",
"hooks": [{"type": "command",
"command": "python3 ${CLAUDE_CONFIG_DIR:-$HOME/.claude}/skills/fable-mode/hooks/fable_spawn_guard.py"}]}],
"PostToolUse": [{"matcher": "Bash",
"hooks": [{"type": "command",
"command": "python3 ${CLAUDE_CONFIG_DIR:-$HOME/.claude}/skills/fable-mode/hooks/fable_fail_streak.py"}]}],
"Stop": [{"hooks": [{"type": "command",
"command": "python3 ${CLAUDE_CONFIG_DIR:-$HOME/.claude}/skills/fable-mode/hooks/fable_close_guard.py"}]}]
}
The skill alone is enough to trigger fable-mode by asking for it; skip the hooks if you only want the protocol.
When a user asks you to install fable-mode from this repo:
$CLAUDE_CONFIG_DIR if set, else ~/.claude.git clone the repo into <config-dir>/skills/fable-mode.bash <config-dir>/skills/fable-mode/install.sh — it merges the hooks
idempotently and resolves paths itself. If you instead register hooks by
editing settings.json yourself, merge into the existing hooks object
(never overwrite the file) and use the absolute clone path — do not
hardcode ~/.claude if the user relocated their config..fable/ directory.Trigger the skill by asking for it by name — "use fable mode", "work like
Fable 5", "rigorous mode", or the Chinese equivalents ("用 fable 模式",
"严谨模式"). It deliberately does not auto-trigger just because a task is
big or important — no surprise process tax; at most it may offer to enable
itself. The other explicit path is a project armed with .fable/, where the
hooks carry the