Skip to content

Folders and files

NameName
Last commit message
Last commit date

Latest commit

 

History

3 Commits
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 

Repository files navigation

goalkeeper

Goals for Claude Code that survive the session, enforce a budget, and refuse to close without evidence.

License: MIT Claude Code plugin Node Dependencies

A port of the goal engine from openai/codex (codex-rs/ext/goal, codex-rs/prompts/templates/goals), rebuilt on Claude Code's hook surface — plus the parts codex does not have: durable state, budgets beyond tokens, mechanical stall detection, a progress ledger, and a completion call that will not fire without evidence.

You give it an objective. It keeps driving turns toward that objective, on its own, until the work is verifiably done — or until it runs out of budget, hits a real impasse, or you stop it.


Install

/plugin marketplace add redstone-md/goalkeeper
/plugin install goalkeeper@goalkeeper

Restart Claude Code so the hooks load. Requires Node ≥ 18 on PATH; no dependencies.

Install from a local clone instead
git clone https://github.com/redstone-md/goalkeeper.git
/plugin marketplace add /absolute/path/to/goalkeeper
/plugin install goalkeeper@goalkeeper

Update later with /plugin marketplace update goalkeeper. Remove with /plugin uninstall goalkeeper.

Use

/goalkeeper:goal Port the auth service to OAuth2 and get the integration suite green

That is the whole workflow. The goal is now active and the loop runs itself.

Command What it does
/goalkeeper:goal <objective> set the goal and start driving turns
/goalkeeper:goal status, usage, ledger
/goalkeeper:goal edit <objective> replace the objective in place
/goalkeeper:goal pause · resume stop / restart automatic continuation
/goalkeeper:goal budget --tokens 800000 --turns 40 --minutes 120 set or raise budgets
/goalkeeper:goal queue <objective> run it after the current goal completes
/goalkeeper:goal log · report progress ledger · full summary
/goalkeeper:goal clear drop the goal
/goalkeeper:goal config --maxContinuations 50 --stallLimit 4 tune the loop

Only the model closes a goal out, and only through the CLI — the exact commands, with the absolute plugin path, are printed when the goal is set and repeated in every continuation prompt:

node <plugin>/lib/cli.js complete --evidence "<one line of proof per requirement>"
node <plugin>/lib/cli.js block --reason "<specific unmet external condition>"

How it works

codex goalkeeper
ThreadGoal row in SQLite, per thread state.json per project root, under ~/.claude/goalkeeper/
on_thread_idlecontinue_if_idletry_start_turn_if_idle Stop hook → {"decision":"block","reason":<prompt>}
continuation.md steering item same prompt, re-rendered each turn with live budget + ledger
TokenUsageContributor usage parsed out of the session transcript JSONL
budget_limited status + wrap-up prompt same, plus turn and wall-clock budgets
update_goal(status) tool cli.js complete / block, evidence required
on_thread_resume SessionStart hook (startup, resume, and compact)
continuation deferral row interrupt detection + UserPromptSubmit clearing the deferral

What it adds over codex

  • Survives everything. codex ties a goal to one thread. Here the goal lives on the project, so /clear, a crash, a new terminal or an auto-compaction do not lose it — SessionStart reinjects it and UserPromptSubmit keeps the objective in context as the window rolls.
  • Three budgets, all enforced. codex enforces tokens only (time is tracked but never trips). goalkeeper enforces tokens, turns and wall clock, and hard-caps automatic continuations (maxContinuations, default 30) so an unbudgeted goal cannot spin forever.
  • Mechanical stall detection. codex learns about an impasse only if the model self-reports it. goalkeeper fingerprints the workspace (HEAD + git status + diff --stat) every turn. One no-change turn injects a change-approach prompt; stallLimit of them (default 3) marks the goal blocked instead of burning budget on a loop.
  • A progress ledger. Every continuation records tokens, tool calls, touched files and whether the workspace moved. The completion audit has something to audit against, and the last few entries ride along in the continuation prompt so the model can see it is repeating itself.
  • Evidence-gated completion. complete without --evidence exits non-zero. The evidence line is stored on the goal and printed in report. Optional adversarial verification via the bundled goal-auditor subagent.
  • A queue. Chain objectives; the next one activates when the current completes.

What it keeps from codex, deliberately

  • The objective is quoted as untrusted data in every prompt, never as instructions.
  • The fidelity clause: no shrinking the objective to what fits in this turn, no substituting an easier task that happens to pass the current tests.
  • The completion audit: requirement by requirement, current-state evidence, uncertain evidence counts as not achieved.
  • The blocked audit: three consecutive turns of the same blocker before blocked is allowed, and never blocked just because the work is hard.
  • Long objectives (>4000 chars) spill to a sidecar file; the goal stores a read-this-file reference.

Safety and cost

  • The Stop hook restarts turns repeatedly. That is the point, and it costs tokens. Set a budget: /goalkeeper:goal budget --tokens 500000. Even unbudgeted, the loop stops after 30 continuations.
  • Esc defers the loop: an interrupted turn is not re-blocked, and the goal picks up on your next message.
  • pause stops continuation immediately; clear removes the goal.
  • Any hook error is swallowed and exits 0 — a broken goal can never wedge a session.
  • Nothing leaves the machine. State is a local JSON file (/goalkeeper:goal path).

Layout

.claude-plugin/plugin.json   plugin manifest
commands/goal.md             /goalkeeper:goal
agents/goal-auditor.md       adversarial completion auditor (read-only)
hooks/                       stop.js · prompt.js · session-start.js · hooks.json
lib/                         state · usage accounting · engine · render · cli
templates/                   continuation · budget-limit · objective-updated · stalled · session-card
test/smoke.js                19 end-to-end checks

Prompts live in templates/ as plain Markdown — edit them to change how the loop talks.

Development

node test/smoke.js

19 end-to-end checks over the CLI and all three hooks, in a throwaway CLAUDE_CONFIG_DIR. No test framework, no dependencies.

License

MIT

About

Persistent, budgeted, evidence-audited goals for Claude Code — a port of the codex /goal engine

Topics

Resources

Stars

1 star

Watchers

0 watching

Forks

Releases

Packages

Contributors

Languages