Skip to content

About

No description, website, or topics provided.

Resources

Stars

0 stars

Watchers

0 watching

Forks

Latest commit

 

History

434 Commits

Folders and files

Repository files navigation

Agent Plan

Agent Plan is a local, project-scoped planning platform for AI coding agents.

It gives a project a structured planning workspace in .planner/, then exposes that workspace through multiple surfaces:

  • a core TypeScript library (@agent-plan/core);
  • a local HTTP/WebSocket server and React dashboard;
  • a Pi adapter with a grouped /planner ... command;
  • a Claude Code MCP server with planner-* tools;
  • a Claude Code /planner ... slash command router;
  • a CLI (agent-plan) for setup, MCP startup, and project initialization.

The goal is to make planning durable, inspectable, and shared across agents without coupling the core planning model to any one harness.


Status

This project is under active development.

Current focus:

  • Pi integration is available through a grouped /planner command.
  • Claude Code integration is available both as a self-hosted plugin (marketplace) and via MCP + a generated /planner slash command.
  • The canonical project data directory is .planner/.
  • Agent Plan intentionally does not read, migrate, or use .plan/; that directory belongs to other tools such as GSD/get-shit-done.

Core concepts

.planner/ is the source of truth

Agent Plan stores structured planning data in the target project:

my-project/
  .planner/
    manifest.json
    project.json
    features.json
    requirements.json
    phases/
      <phase-id>.json
    resume.json
    handoff-archive/
    generated/
      PLAN.md
      features/
      phases/

JSON files are the source of truth. Markdown files under .planner/generated/ are generated views for humans and agents.

Hierarchy

The public planning hierarchy is:

project → features → phases → tasks

Requirements currently exist as internal/project seed data and are not exposed as public Claude Code commands in Phase 1.

Harness-agnostic core

The core planning model lives outside Pi, Claude Code, or any other harness. Adapters should call shared planning logic rather than owning business rules.

Several agents on one planner

Each agent session (a Claude Code or Codex MCP connection, a Pi session) keeps its own focus:

  • Tasks: a task in progress belongs to the session that started it.
  • Side tasks: when a session switches to a temporary task (task_switch, task_deviation), the task to return to is recorded for that session only. Another session's recommendation never says RESUME REQUIRED for it and never offers the set-aside task, so one agent's detour does not become another agent's order.
  • Resume focus: each session has its own current phase, in-progress tasks, next steps and notes (.planner/.local/resume-sessions.json, the 20 most recent sessions are kept). A session that has none yet starts from the project-level focus. The guard bypass stays project-wide.

A caller with no session (the web UI, scripts) sees the whole project, as before. Work recorded before sessions were tracked is shown to every session. A checkpointed task that no live side task points at is still offered to every session, so paused work is not lost.

Task starts claim ownership atomically. Repeating a start succeeds only for the owning caller; another caller gets started: false with TASK_OWNED_BY_ANOTHER_SESSION. A stdio MCP restart creates a new caller identity. After confirming the previous caller has stopped, use planner-session-recover with { task: "P001(F001)/T001", confirmed: true } (Pi: session_recover with taskId). The task can be the old active task or a pending return task. Recovery transfers the old caller's owned tasks, complete deviation stack and saved focus into the fresh caller without changing task statuses or checkpoints. Read context and call task-start normally afterward. No client-side owner-ID mapping is needed.

Recovery refuses a registered process that is still alive, a process on another host whose exit cannot be checked, or a destination caller that already owns work. Older releases have no process record; for those sessions, explicit confirmation is the operator's assertion that the old caller has stopped. This operation is available through MCP/Pi and the core; the read-only /api/v1 remains unchanged.


Documentation

Plugins

Agent Plan is distributed to AI coding harnesses through a self-hosted plugin marketplace. Plugins are static bundles (JSON + Markdown + shell scripts) living in the top-level plugins/ directory, separate from the npm packages in packages/.

How plugins work

A plugin does not reimplement planning logic. It wires a harness to the shared planning core (@agent-plan/mcp, the MCP stdio server, backed by @agent-plan/core) and provides harness-specific integration: command/skill routing where the harness supports it, lifecycle notifications where available, and the MCP server declaration.

plugins/
  claude-code/                 Claude Code plugin (ready)
    .claude-plugin/plugin.json   plugin manifest
    .mcp.json                     @agent-plan/mcp stdio server (npx)
    skills/planner/SKILL.md       /planner routing (derived from _shared/)
    hooks/hooks.json              SessionStart non-blocking notify
    scripts/notify-session-start.sh
  codex/                      Codex plugin (ready: MCP + skill)
    plugin.json                 portable Agent Plugins manifest
    .codex-plugin/plugin.json   Codex compatibility manifest
    mcp.json / .mcp.json        @agent-plan/mcp stdio server (npx)
    skills/agent-plan/SKILL.md  Agent Plan skill (derived)
    skills/planner/SKILL.md     $planner alias skill (derived)
  opencode/                   OpenCode bundle (ready: MCP + commands)
    skills/agent-plan/SKILL.md  Agent Plan skill/guide (derived)
  _shared/                    single-source-of-truth templates
    planner-skill.md.in
    notify-session-start.sh.in
.claude-plugin/marketplace.json   marketplace catalog (repo root, per Claude Code spec)
.agents/plugins/marketplace.json  Codex marketplace catalog (repo root)

Per-harness behavior:

  • The planner is disabled by default; nothing auto-starts.
  • /planner load — enable the planner, start the web dashboard (LAN-bound, dynamic port), emit a recap (status + handoff + Web UI address).
  • /planner stop (alias /planner disable) — disable the planner and stop the web.
  • The Web UI address is shown only on the load recap or via /planner web status — never appended to every message.
  • Planner operations (handoff, plan CRUD) are not code edits and are always allowed regardless of task state.
  • Claude Code and OpenCode support /planner routing. OpenCode also installs flat autosuggest shortcuts such as /planner-load and /planner-task-start.
  • Codex currently exposes Agent Plan through MCP tools and the agent-plan / planner skills ($planner appears in the Codex skill picker); custom /planner ... slash-command registration is not part of the public Codex plugin/config surface.

Install (Claude Code, self-hosted marketplace — no approval required)

/plugin marketplace add ovidius72/agent-planner
/plugin install agent-plan@agent-plan-marketplace

Install (Codex marketplace)

The CLI setup below installs the Codex marketplace plugin automatically at user scope when the codex CLI is available. Manual equivalent:

codex plugin marketplace add https://github.com/ovidius72/agent-planner \
  --ref main \
  --sparse .agents/plugins \
  --sparse plugins/codex
codex plugin add agent-plan@agent-plan

Update

The plugin version is bumped by the release scripts together with the npm packages — pnpm release for the stable channel and pnpm release:next for the next prerelease channel (the plugin has its own version track, independent from the npm package versions). The Claude Code plugin manifests, Codex plugin manifests, .claude-plugin/marketplace.json, and .agents/plugins/marketplace.json are updated, so marketplace clients detect the new version and refresh the plugin files. The MCP server auto-updates independently because plugin MCP declarations run npx -y @agent-plan/mcp, which fetches the latest published @agent-plan/mcp from npm.

As a user — after a new release is merged to main, refresh in Claude Code:

/plugin marketplace update

Then restart Claude Code in the project so the MCP server re-launches with the new @agent-plan/mcp.

For Codex, run:

agent-plan setup codex --user --force

Then restart Codex and verify with planner-version. If the planner web UI is missing recently released dashboard sections, the active MCP process is usually stale; planner-version shows the version Codex actually loaded.

As a maintainer — run the release script for the target channel (pnpm release for stable, pnpm release:next for next). It bumps the plugin versions in the Claude Code and Codex plugin manifests plus both marketplace catalogs. Do not edit the version fields by hand: the scripts own them, and an unchanged pinned version can make marketplace clients report "already at the latest" and skip the refresh.

Local development / testing

claude --plugin-dir ./plugins/claude-code --debug

Or add the repo itself as a local marketplace:

/plugin marketplace add ./
/plugin install agent-plan@agent-plan-marketplace

Scaffolding a new harness plugin

  1. Add a subdirectory under plugins/<harness>/ with the harness manifest/config files, MCP wiring, and skills/.
  2. Add an entry to the HARNESSES table in scripts/sync-plugins.cjs.
  3. Edit the templates in plugins/_shared/ (never edit derived files directly).
  4. Run pnpm plugins:sync to regenerate derived files (pnpm plugins:check for the CI drift guard).

See plugins/README.md and plugins/DECISIONS.md for the full design and decision record.


Recommended Claude Code setup

Prefer the plugin — the self-hosted marketplace plugin (see Plugins above) is now the recommended install path: /plugin marketplace add ovidius72/agent-planner then /plugin install agent-plan@agent-plan-marketplace. The CLI-based setup below remains a valid manual alternative and is still used to register the MCP server, slash command, and write guard hook at user/project scope.

1. Install once

After publication, the intended installation is:

npm install -g agent-plan

Then configure Claude Code once at user scope:

agent-plan setup claude-code --user

This does three things:

  1. registers the Agent Plan MCP server in Claude Code user scope;
  2. writes the Claude Code slash command router:
~/.claude/commands/planner.md
  1. installs a Claude Code PreToolUse task guard hook in:
~/.claude/settings.json

After this, /planner ... is available from Claude Code projects and implementation tools are guarded when a project has an active .planner/.

2. Initialize a project only when needed

Open a project with Claude Code:

cd my-project
claude

Then initialize planning explicitly:

/planner init

This creates:

my-project/.planner/

If a project is not initialized, Agent Plan tools should report that .planner/ is missing and suggest /planner init.


User commands — Claude Code

Claude Code supports a slash command /planner ... that routes natural command text to the underlying MCP tools.

Core

  • /planner init — Initialize planner
  • /planner show — Show planner overview
  • /planner repair — Repair planner integrity
  • /planner load — Re-enable planner
  • /planner disable — Disable planner for this session

Project

  • /planner project discuss — Run project discovery
  • /planner project language — Set persistent language preferences

Features

  • /planner feature list — List features
  • /planner feature add <name> — Create a feature
  • /planner feature show <id> — Show a feature
  • /planner feature update <id> — Update a feature
  • /planner feature delete <id> — Delete a feature

Phases

  • /planner phase list — List phases
  • /planner phase add <title> — Add a phase
  • /planner phase show <id> — Show a phase
  • /planner phase discuss <id> — Discuss a phase
  • /planner phase update <id> — Update a phase
  • /planner phase delete <id> — Delete a phase

Tasks

  • /planner task list — List tasks
  • /planner task add <title> — Add a task
  • /planner task show <id> — Show a task
  • /planner task discuss <id> — Discuss a task
  • /planner task update <id> — Update a task
  • /planner task delete <id> — Delete a task
  • /planner task start <id> — Mark a task in-progress
  • /planner task complete <id> — Mark a task done

Handoff

  • /planner handoff list — List phases with a handoff
  • /planner handoff prepare — Tell the agent to create/update the handoff
  • /planner handoff show — Show the current handoff
  • /planner handoff write — Write handoff from planner data
  • /planner handoff clear — Delete the current handoff

Export & Web

  • /planner export — Export plan summary as Markdown
  • /planner export-full — Export full detailed plan as Markdown
  • /planner web start|stop|status — Manage the web UI

Guard bypass

  • /planner bypass — Authorize edit/write without a task (15 min)
  • /planner clear-bypass — Revoke the bypass

Agent tools (MCP)

The MCP server exposes public tools using the planner-* namespace. These tools are called by AI agents (Claude Code, Codex, Zed, OpenCode), not by humans. Human users should use /planner ... where the harness supports custom commands (Claude Code and OpenCode), or the agent-plan skill / natural-language planner requests in Codex.

Current Phase 1 tools include:

Core

  • planner-init
  • planner-show
  • planner-description-freshness — non-mutating child-to-parent drift preview with exact stale refs
  • planner-repair
  • planner-load
  • planner-disable
  • planner-web

Project

  • planner-project-discuss
  • planner-project-language

Features

  • planner-feature-list
  • planner-feature-add
  • planner-feature-show
  • planner-feature-update
  • planner-feature-delete

Phases

  • planner-phase-list
  • planner-phase-add
  • planner-phase-show
  • planner-phase-discuss
  • planner-phase-update
  • planner-phase-delete

Tasks

  • planner-task-list
  • planner-task-add
  • planner-task-checklist-add (append one step; next C{n}, stable id)
  • planner-task-checklist-remove (remove one step by C{n}/id/title; renumber C1..Cn)
  • planner-task-checklist-toggle (tick/untick a step by C{n}/id/title; no list rewrite)
  • planner-task-show
  • planner-task-discuss
  • planner-task-update
  • planner-task-delete
  • planner-task-start
  • planner-task-complete

Handoff

  • planner-handoff-list
  • planner-handoff-prepare
  • planner-handoff-show
  • planner-handoff-write
  • planner-handoff-verify
  • planner-handoff-clear

planner-handoff-list indexes active handoffs. planner-handoff-show <phaseRef> also recovers the latest terminal archive after a phase becomes done, rejected, or canceled, preserving discoverability of closeout content and linked .planner/docs/ references.

Export

  • planner-export (with optional full boolean for detailed hierarchical output)

Guard bypass

  • planner-authorize-bypass (temporary bypass so Edit/Write work without a task in-progress)
  • planner-clear-bypass

Requirements are intentionally not exposed as planner-requirement-* in Phase 1.

The current Phase 1 count is 38 public planner-* tools.


Claude Code setup modes

User-scope setup, recommended

Use this once per machine/user:

agent-plan setup claude-code --user

This keeps the MCP server and slash command available across projects.

It does not create .planner/ in any project.

Project-local setup

Use this when you want a repository-local Claude Code configuration, for example for a team, a pinned version, or local development:

agent-plan setup claude-code --project

This creates or updates:

.mcp.json
.claude/commands/planner.md
.claude/settings.json

The settings file contains a Claude Code PreToolUse hook for Edit|Write and the shared guard-bypass flow.

Example .mcp.json:

{
  "mcpServers": {
    "agent-plan": {
      "command": "npx",
      "args": ["agent-plan", "mcp"]
    }
  }
}

Project-local setup also does not initialize .planner/. Run /planner init when you want planning enabled in that repo.

Recommended Codex setup

Install Agent Plan globally from npm:

npm install -g agent-plan

Then configure Codex once at user scope:

agent-plan setup codex --user --force

Use --force when repairing an existing Codex install. It rewrites the agent-plan MCP entry and removes legacy per-tool approval tables such as [mcp_servers.agent-plan.tools.planner-task-recommend], which can otherwise make Codex ask for permission on every planner tool call.

For a single project, run this inside that project instead:

agent-plan setup codex --project --force

This writes Codex MCP configuration to .codex/config.toml or ~/.codex/config.toml, installs the agent-plan and planner skills, and for user scope registers/installs the Codex marketplace plugin when the codex CLI is available. Use --local only when testing an unpublished checkout build; in that mode the Codex marketplace source is the local repository checkout. Restart Codex after setup so already-running sessions reload the Agent Plan MCP process. Verify the runtime from inside Codex with planner-version; the loaded @agent-plan/mcp version should match the released npm version you expect.

Recommended OpenCode setup

Install Agent Plan globally from npm:

npm install -g agent-plan

Then configure OpenCode once at user scope:

agent-plan setup opencode --user --force

For a single project, run this inside that project instead:

agent-plan setup opencode --project --force

This writes OpenCode MCP configuration plus /planner command routing under OpenCode's command configuration key. OpenCode also gets flat shortcut aliases such as /planner-load, /planner-task-start, and /planner-web-start for command-list discovery. The generated command templates are compact and do not paste the full planner guide on every invocation. Use --local only when testing an unpublished checkout build.

Local development setup

For unpublished local changes, use the built local CLI:

pnpm --filter @agent-plan/core build
pnpm --filter @agent-plan/server build
pnpm --filter @agent-plan/mcp build
pnpm --filter agent-plan build

Project-local local setup:

node /Users/antonio/projects/agent-plan/packages/agent-plan/dist/index.js setup claude-code --project --local
node /Users/antonio/projects/agent-plan/packages/agent-plan/dist/index.js setup codex --project --local
node /Users/antonio/projects/agent-plan/packages/agent-plan/dist/index.js setup opencode --project --local

User-scope local setup:

node /Users/antonio/projects/agent-plan/packages/agent-plan/dist/index.js setup claude-code --user --local
node /Users/antonio/projects/agent-plan/packages/agent-plan/dist/index.js setup codex --user --local
node /Users/antonio/projects/agent-plan/packages/agent-plan/dist/index.js setup opencode --user --local

CLI

The CLI package is agent-plan.

agent-plan help
agent-plan --version       # alias: -v
agent-plan mcp
agent-plan init [name] [--description <text>] [--goal <text>] [--json]
agent-plan serve [--root <.planner dir>] [--port <n>] [--host <h>] [--reuse] [--json]
agent-plan stop [--root <.planner dir>] [--json]
agent-plan export [--full]
agent-plan setup claude-code --user
agent-plan setup claude-code --project

Version reporting

Report the installed CLI package:

agent-plan --version       # alias: agent-plan -v

Report the versions loaded by each harness:

# Pi
/planner version

# Claude Code plugin
/planner version

# Claude Code or Codex through MCP
planner-version

The MCP result identifies the loaded @agent-plan/mcp and @agent-plan/core packages. Pi also identifies the loaded @agent-plan/pi-adapter and @agent-plan/server packages. To inspect Pi's installed package directly from a shell:

npm --prefix "$HOME/.pi/agent/npm" list @agent-plan/pi-adapter --depth=0

agent-plan mcp

Starts the stdio MCP server.

This is what Claude Code launches after setup.

agent-plan init

Initializes .planner/ in the current working directory.

cd my-project
agent-plan init

This is equivalent in intent to running /planner init from an agent UI.

For programs, --description and --goal set the project fields when the planner is created, and --json prints one line: {"status":"created"|"exists","root":...,"name":...}. With --json the command never prompts (the folder name is the default name). An existing planner is never changed: it reports "exists" with exit code 0.

agent-plan serve

Starts the planner web server for a .planner/ folder and prints its address. It runs until stopped (Ctrl-C or SIGTERM).

agent-plan serve                       # ./.planner on 127.0.0.1:3030
agent-plan serve --port 0 --json       # any free port; one JSON line on stdout
agent-plan serve --root /path/to/.planner --host 0.0.0.0

--json prints {"url","localUrl","lanUrl","host","port","root","reused"} (with the real port when --port 0). A missing .planner/ or an invalid port exits with code 1 and a message on stderr.

While a server runs it writes .planner/.local/server.json (pid, address, root, start time, version, kind) and removes it when it stops. The file is git-ignored, and a record whose process is gone or whose address no longer answers /health is ignored. Every server writes it, whether it was started by agent-plan serve, by planner-web / planner-load, or by the Pi adapter. When two servers run for one folder, the first keeps the record.

agent-plan serve --reuse --json   # a server is already running for this folder: print its address (reused: true) and exit
agent-plan stop                   # stop the server that `agent-plan serve` started for this folder

serve --reuse starts a server only when none is running. stop only stops a server started by agent-plan serve (kind: "standalone"). A server running inside another program (an agent's MCP server, the Pi adapter) is kind: "embedded": stop refuses (exit 1) because signalling it would end that program; stop it from there (planner-web stop, /planner stop). stop exits 0 when nothing is running.

agent-plan export

Generates a Markdown export of the plan and writes it to .planner/EXPORT.md.

agent-plan export          # summary report
agent-plan export --full   # full hierarchical detail (features → phases → tasks)

In Pi and Claude Code the same report is available via:

/planner export
/planner export-full

The web UI also exposes an Export dropdown with Summary and Full options that download the generated Markdown file.

agent-plan setup claude-code

Configures Claude Code integration.

Useful options:

--user      install at Claude Code user scope
--project   install in the current project; this is the default
--local     point config to the local built CLI instead of npx/global package
--force     overwrite an existing agent-plan MCP entry

User commands — Pi

Pi exposes Agent Plan as one grouped command:

/planner

Core

  • /planner init — Initialize planner in this project
  • /planner show — Show planner overview
  • /planner repair — Repair planner integrity
  • /planner load — Re-enable planner and start web UI
  • /planner disable — Disable planner and stop web UI for this session (alias: /planner stop)

Project

  • /planner project discuss — Run project discovery
  • /planner project language — Set persistent language preferences

Features

  • /planner feature list — List features
  • /planner feature add — Create a feature
  • /planner feature show — Show a feature
  • /planner feature update — Update a feature
  • /planner feature delete — Delete a feature

Phases

  • /planner phase list — List phases
  • /planner phase add — Add a phase
  • /planner phase show — Show a phase
  • /planner phase discuss — Discuss a phase
  • /planner phase update — Update a phase
  • /planner phase delete — Delete a phase

Tasks

  • /planner task list — List tasks
  • /planner task add — Add a task
  • /planner task show — Show a task
  • /planner task discuss — Discuss a task
  • /planner task update — Update a task
  • /planner task delete — Delete a task
  • /planner task start — Mark a task in-progress
  • /planner task complete — Mark a task done

Handoff

  • /planner handoff list — List phases with a handoff
  • /planner handoff prepare — Tell the agent to create/update the handoff
  • /planner handoff show — Show the current handoff
  • /planner handoff write — Write handoff directly from planner data
  • /planner handoff clear — Delete the current handoff

Web

  • /planner web start — Start the web UI
  • /planner web stop — Stop the web UI
  • /planner web status — Show web UI status

Export

  • /planner export — Export plan summary as Markdown
  • /planner export-full — Export full detailed plan as Markdown

Guard bypass

  • /planner bypass — Authorize edit/write without a task in-progress (15 min)
  • /planner clear-bypass — Revoke the guard bypass

Pi startup behavior and resume

The planner is disabled by default at Pi startup. No enablement or web-UI prompt is shown — nothing auto-starts. To enable the planner, the user (or agent) runs /planner load; to disable it, /planner stop (alias /planner disable).

Why this exists:

  • Pi sessions should be quick to resume without blocking prompts;
  • the planner must not start automatically — only on explicit request;
  • the same model applies consistently across harnesses (Pi, Claude Code, Codex).

When the planner is loaded, the startup resume summary includes the dashboard URL (LAN address + port). The Web UI address appears only in that load recap or via /planner web status — never appended to every message.

If no feature/phase/task is actually in-progress, the resume summary must not invent a current focus from the handoff. In that case, the handoff is treated as a previous-session hint to validate against the current plan state, ordering, and dependencies.

Stable planning order and visible numbering

Agent Plan now persists explicit planning order for:

  • features → feature.number
  • phases → phase.number
  • tasks → task.number

This order is displayed as stable human-friendly labels:

  • F001, F002, ...
  • P001, P002, ...
  • T001, T002, ...

Why this exists:

  • UUIDs are stable but hard to reason about visually;
  • resume, handoff, export, and Work Tree must agree on the same ordering;
  • teams need a clear sense of sequence and priority, not just identity.

For older projects, the numbering is normalized automatically from the current planner structure and persisted back into .planner/.

Older flat slash commands such as planner-task-start were removed from Pi's global command registration to avoid autocomplete noise. Pi users should use the grouped /planner ... form.


Web UI

Agent Plan includes a local web UI served by plan-server and used by the Pi adapter.

The web UI visualizes:

  • project summary;
  • features;
  • phases;
  • tasks;
  • status rollups;
  • accepted decisions;
  • handoff state.

The planner-web MCP tool fully manages the web lifecycle (start / status / stop) in-process, binding LAN (0.0.0.0) with a dynamic OS-assigned port. Every start/status response returns the reachable address plus typed running/address/localUrl/lanUrl/host/port/mode metadata (Pi parity). The same lifecycle is exposed in the Pi adapter as agent tools (planner-web, planner-load, planner-stop) and as /planner web / /planner load / /planner stop slash commands.

Planner housekeeping

Agent Plan now creates a project-local ignore file at:

.planner/.gitignore

It ignores transient planner artifacts such as:

  • *.bak
  • *.tmp.*

Why this exists:

  • PlanStore uses atomic writes and backup files for safety;
  • backup/temp artifacts should not pollute git status;
  • planner recovery should stay safe without requiring manual cleanup.

At Pi session start, orphan .bak and *.tmp.* files are also cleaned up asynchronously in the background. This is automatic; there is no manual command to run.


Handoff workflow

Handoffs are entity-scoped: each phase carries its own phase.handoff field (stored inline in the phase JSON), not a standalone file. The legacy .planner/HANDOFF.md is deprecated. The last 5 cleared handoffs per phase are archived under .planner/handoff-archive/ for recovery.

Slash commands (/planner handoff ...):

  • /planner handoff list — list phases with a non-empty phase.handoff
  • /planner handoff show <P00x(F00x)> — read one exact phase handoff and its resume-readiness status
  • /planner handoff write <P00x(F00x)> — route agents through prepare/write; direct unsynchronized writes are disabled
  • /planner handoff prepare — tell the agent to prepare a candidate for one explicitly confirmed phase
  • /planner handoff clear <P00x(F00x)> — archive and clear a phase handoff

MCP tools:

  • planner-handoff-list
  • planner-handoff-show
  • planner-handoff-write
  • planner-handoff-prepare
  • planner-handoff-verify
  • planner-handoff-clear

Lifecycle: a handoff is archived when its phase reaches any terminal outcome. A confirmed write persists a candidate with resumeReady: false; the agent must show and read the complete persisted body, compare it again with all required sources, then call the verify tool with the shown content hash. Only resumeReady: true permits a completeness claim. On resume it remains context to validate against current plan state, not a lock—task_start is never blocked by a pending handoff.

New handoffs are compact resume capsules targeting at most 8,000 inline characters (24,000 remains only as an absolute compatibility ceiling). Inline sections are: Current focus, Current and partial state, Preservation constraints, Supporting documents, Blockers and risks, and How to resume. The verbose completeness audit and cold-start inventory are retained once as structured metadata and never embedded in Markdown. Oversized writes auto-externalize the full body to one planner-owned .planner/docs/handoff-*.md document and complete the write; there is no dead-end size error. Supporting .planner/docs/*.md references render as new-tab links in shared formatted content and open the path-safe viewer at /docs/view (traversal/symlink rejected); the viewer includes a dependency-free textarea editor with live preview and an explicitly confirmed save (confirmed=true). Editor decision: @uiw/react-md-editor and CodeMirror 6 were evaluated and rejected to avoid bundle/maintenance cost; the baseline textarea plus existing preview is the shipped editor.


Task status discipline

Agent Plan relies on explicit task lifecycle transitions.

Before implementation work:

/planner task start <task-id>

Before temporarily changing focus:

task_switch(from_task, to_task, reason, what_was_being_done, resume_location, how_to_resume)

This deliberately allows necessary non-priority work while changing the source task to paused with a durable checkpoint. Temporary switches form a LIFO return stack; completing the temporary task emits RESUME REQUIRED and makes the preserved source the next recommendation. Use task_pause when no temporary target is being started.

After completed work:

/planner task complete <task-id>

Phase and feature statuses are derived from child task/phase state. Agents should not directly mutate parent status unless there is a specific reason.

Why this matters:

  • the dashboard header and Work Tree use active task state;
  • feature/phase rollups are derived from child tasks;
  • resume focus and handoff quality depend on correct task lifecycle transitions;
  • if an agent edits code without moving a task to in-progress/done, the whole planner tree becomes stale.

For this reason, Agent Plan provides dedicated lifecycle tools and blocks the wrong path:

  • use task_start / planner-task-start / /planner task start to begin or resume work;
  • use task_pause / planner-task-pause to save why work stopped, what was underway, the exact resume location, and how to continue;
  • use task_switch / planner-task-switch to override normal feature → phase → task priority without losing the active task context;
  • use task_complete / planner-task-complete / /planner task complete to finish work and surface any required return target;
  • do not use task_update to move a task directly to in-progress, paused, or done.

No-task warning and temporary bypass

Agent Plan never blocks a tool call and never asks the user to confirm one because of task state. When a call changes the project's code (a file inside the project, outside .planner/) and no task is in-progress, the agent gets a warning telling it which task to start. The call goes through either way.

  • Planner changes never need a task: CRUD on the project, features, phases, tasks, requirements, decisions and handoffs, and any write under .planner/.
  • Writes outside the project never warn: /dev/null, ~/.claude/..., temp folders, other repositories.
  • Read-only commands never warn: git pull, build, test, search, inspection.
  • An authorized temporary bypass silences the warning for its window.

Recommended workflow:

  1. Start the task normally:
/planner task start <task-id>
  1. If the user explicitly wants work without opening a task, authorize a temporary bypass:
/planner bypass
  1. Do the edit/write work.

  2. Revoke the bypass when you want normal discipline back:

/planner clear-bypass

The same flow is available through low-level tools:

  • Pi/runtime tools: plan_authorize_bypass, plan_clear_bypass
  • Claude/MCP tools: planner-authorize-bypass, planner-clear-bypass

The bypass is stored in .planner/resume.json as guardBypassUntil, so it is shared across harnesses and auto-expires.

Claude Code task guard

agent-plan setup claude-code (and the Claude Code plugin) installs a PreToolUse hook for Edit|Write|NotebookEdit|Bash. It never blocks and never prompts: when a call changes project code while no task is in-progress, it adds a warning to the agent's context and sets no permission decision, so Claude Code's normal permission flow is unchanged. Bash counts only when the command writes (redirect, tee, sed -i, cp/mv, rm, tree-rewriting git) into the project.

To silence the warning for a while, authorize a bypass:

/planner bypass

or via MCP:

planner-authorize-bypass  (default 15 minutes)

Revoke:

/planner clear-bypass
planner-clear-bypass

The bypass is harness-agnostic (stored in resume.json), so Pi, Claude Code, Codex and other adapters all respect it.


Repository structure

packages/
  agent-plan/      CLI: agent-plan mcp/init/setup
  plan-core/       schemas, persistence, rendering, status logic
  plan-server/     local HTTP/WebSocket server
  plan-web-ui/     React dashboard
  plan-mcp/        MCP stdio server for Claude Code
  pi-adapter/      Pi extension adapter
plugins/
  claude-code/     Claude Code plugin (marketplace bundle)
  codex/           Codex plugin bundle (MCP + skill)
  opencode/        OpenCode setup/plugin bundle (MCP + commands)
  _shared/         single-source-of-truth templates for plugins
.claude-plugin/marketplace.json   self-hosted marketplace catalog (repo root)
scripts/
  release.cjs      unified release helper (pnpm release)
  sync-plugins.cjs regenerate plugin derived files from _shared/
  copy-web-ui.sh   copy Vite build into server/adapter web-ui-dist

Important docs:

PROJECT.md
ROADMAP.md
AGENTS.md
plugins/README.md
plugins/DECISIONS.md
docs/multi-agent-strategy.md
docs/setup-claude-code.md

Development

Install dependencies:

pnpm install

Build/check all packages:

pnpm check

Build MCP and CLI only:

pnpm --filter @agent-plan/mcp build
pnpm --filter agent-plan build

Smoke test MCP tools locally:

node packages/agent-plan/dist/index.js mcp

For automated MCP smoke testing, use the MCP SDK client to call listTools; the expected Phase 1 count is currently 38 public planner-* tools.

Runtime implementation notes

These behaviors are mainly relevant to contributors extending the adapters:

  • Pi caches its injected planner context block between turns and rebuilds it only on the first turn or after planner writes. This reduces repeated I/O and large prompt regeneration on steady turns.
  • Pi appends a reminder after successful edit/write work when a task is active, nudging the agent to call task_complete when implementation is truly finished.
  • The write guard is intentionally harness-agnostic: the shared source of truth is .planner/resume.json, not a Pi-only in-memory flag.
  • The startup resume summary must mention the dashboard URL when the web UI is active, and must treat handoff targets as hints rather than current focus when nothing is actually in progress.

Troubleshooting

/planner is not available in Claude Code

Check that the slash command exists:

User scope:

~/.claude/commands/planner.md

Project scope:

.claude/commands/planner.md

Then restart Claude Code in the project.

Bash/Edit/Write is blocked in Claude Code

This is expected if .planner/ exists, tasks exist, and no task is in-progress.

Run:

/planner task start <task-id>

Then retry the implementation action.

MCP tools are not available in Claude Code

For project-local setup, check:

.mcp.json

For user-scope setup, check Claude Code's MCP list:

claude mcp list

If needed, re-run:

agent-plan setup claude-code --user --force

Design principles

  • .planner/ is project-local and explicit.
  • Markdown is generated, not the source of truth.
  • Core planning logic must remain harness-agnostic.
  • Pi, Claude Code, and future agents are adapters over the same planning model.
  • Installation should be global/user-level when possible; project initialization should remain explicit.
  • Public naming uses planner-* for MCP tools and /planner ... for human command UX.

Build and publish

This repository is a pnpm workspace. Only some packages are published to npm.

Packages

Published (public npm):

  • @agent-plan/core — schemas, persistence, ordering, status rollups, rendering
  • @agent-plan/mcp — MCP stdio server
  • @agent-plan/server — local HTTP/WebSocket server
  • agent-plan — CLI (init, mcp, setup claude-code, setup codex, setup opencode, export, guard pre-tool-use)
  • @agent-plan/pi-adapter — Pi extension adapter

Private (not published):

  • @agent-plan/web-ui — Vite application, served as a build artifact, not a standalone npm package

Prerequisites

  • Node.js and pnpm installed
  • npm login performed (or NPM_TOKEN configured) on the account that owns the @agent-plan scope

Build and validate

From the repository root:

pnpm install
pnpm release:validate

release:validate runs the full build and the TypeScript check:

pnpm build
pnpm check

The Web UI bundle (web-ui-dist/) is committed on purpose

packages/plan-server/web-ui-dist/ and packages/pi-adapter/web-ui-dist/ contain the built dashboard (a copy of the Vite build of packages/plan-web-ui). They are tracked in git by design, so please do not delete, untrack or git-ignore them:

  • The published @agent-plan/server and @agent-plan/pi-adapter packages ship them, and a plain checkout serves the dashboard without building it.
  • scripts/copy-web-ui.sh finds where to copy the build by looking for these folders. Without them, pnpm build fails on a fresh clone and in CI.

Never edit them by hand. pnpm build regenerates both copies. When you change packages/plan-web-ui/src, commit the regenerated bundle in the same PR as the UI change. If web-ui-dist/ shows up as modified and you did not change the UI, someone has an uncommitted UI change: ask before touching it.

Inspect the published tarballs

Before publishing, inspect what would actually be packaged:

pnpm release:pack-dry-run

Important: use pnpm pack (or pnpm release:pack-dry-run), not npm pack.

pnpm pack/pnpm publish rewrite workspace:* dependency ranges to the real published versions inside the tarball. npm pack leaves workspace:* verbatim, which makes the resulting tarball uninstallable.

The expected tarball contents for each public package are:

  • dist/**/*.js, dist/**/*.d.ts, dist/**/*.d.ts.map
  • README.md
  • LICENSE
  • package.json

src/, tsconfig.json, and dist/.tsbuildinfo must NOT appear in the tarball.

Publish to npm

Publishing is automated by GitHub Actions. The workflow .github/workflows/publish.yml runs on pushes to main and next: main publishes the stable latest channel after a release PR merge, while next publishes prereleases under the next dist-tag. It publishes all five public packages in dependency order using pnpm publish (which rewrites workspace:* ranges to the resolved versions). Merging into develop does not publish — develop is staging. After a successful stable publish from main, the workflow creates the canonical annotated tag vX.Y.Z; prerelease publishes never create stable tags.

Do not run npm publish manually per package: it would publish stale workspace:* ranges that npm cannot install.

Bounded verification

Use the canonical runner instead of repeatedly chaining broad commands:

pnpm verify:focused -- --package plan-mcp
pnpm verify:focused -- --test packages/plan-mcp/test/mcp-harness.test.mjs
pnpm verify:final

Focused mode runs one package or test file. Final mode captures complete logs under .planner/.local/verification/, prints only concise summaries or bounded failure excerpts, and reuses a successful result while the repository content fingerprint is unchanged. The final gate covers build, typecheck, coverage, plugin synchronization, browser E2E, and a clean mkdtemp installation from freshly packed public packages.

Versioning & release

All public packages share a single unified version per release. Releases are driven by the release script (scripts/release.cjs).

From a clean develop branch, up to date with origin:

pnpm release              # patch (default)
pnpm release -- minor      # minor
pnpm release -- major      # major
pnpm release -- 1.0.0      # explicit version
pnpm release -- --dry-run  # preview only

The script does everything:

  1. Pre-flight — clean working tree, on develop, up to date with origin/develop.
  2. Compute the unified target version — fetch canonical vX.Y.Z tags and bump the latest stable tag. While tag history is being bootstrapped, fall back to the unified stable version on origin/main. Develop prerelease suffixes such as -next.N never affect the stable base; explicit versions retain a downgrade guard.
  3. Create release/v<version> from develop and bump all 5 packages to that version.
  4. Verify — pnpm install + the canonical pnpm verify:final gate (bounded logs, build, typecheck, coverage, plugin sync, Playwright, and freshly packed/installed artifact smoke); rolls back the branch on failure.
  5. Commit, push, and open a PR → main.

Merge the release PR into main to trigger publish.yml (npm publish + stable vX.Y.Z tag). Then sync develop:

git switch develop && git pull && git merge origin/main && git push

See AGENTS.md §12 (Branching & Release) for the full rules.

Prerelease (next) channel

For day-to-day iteration, the repo also publishes a next npm dist-tag from the next branch:

pnpm release:next              # bump the prerelease counter (0.2.19-next.10 -> 0.2.19-next.11)
pnpm release:next -- --dry-run  # preview only

scripts/release-next.cjs increments the -next.N prerelease counter on the current branch and pushes; publish.yml publishes the result to npm with the next dist-tag. Install it with:

npm i @agent-plan/core@next

The plugins (plugins/claude-code/.claude-plugin/plugin.json, plugins/codex/plugin.json, plugins/codex/.codex-plugin/plugin.json, and the repo-root marketplace catalogs) have their own version track but are bumped by both release scripts so marketplace clients can detect refreshed plugin files on either channel. Stable Git tags always use the unified npm package version, not the independent plugin version.

Install the published CLI

After publishing, end users install once:

npm install -g agent-plan

Then configure an agent harness, e.g. for Claude Code at user scope:

agent-plan setup claude-code --user

Project initialization stays explicit and is done later inside a project with /planner init or agent-plan init.

About

No description, website, or topics provided.

Resources

Stars

0 stars

Watchers

0 watching

Forks

Releases

Packages

Contributors

Languages