opencode-path
v0.6.3
Published
Structured multi-agent workflow CLI for opencode
Maintainers
Readme
OpenCode Path
A structured multi-agent workflow CLI for opencode that installs specialized agents, configures models, and applies stack-specific permission profiles. Separate concerns, minimize blast radius, and optimize model usage by role.
Overview
The workflow follows a structured pipeline from requirements to reviewed implementation, with optional support paths and a user-invoked audit layer:
Normal path:
User -> Spec -> Architect -> Developer -> Reviewer -> User
Short path for already-clear work:
User -> Architect -> Developer -> Reviewer -> User
Support paths:
Research may support Spec or Architect when docs, APIs, SDK behavior, or facts are needed.
Explore may be invoked by workflow agents for bounded codebase reconnaissance.
Auditor is an optional user-invoked audit path after or alongside implementation.Developer must invoke Reviewer before declaring implementation done. Reviewer returns PASS/FAIL; on FAIL, Developer fixes the findings and asks Reviewer again. Explore is not a primary workflow owner — it is a read-only support subagent for reconnaissance.
This workflow defines specialized agents with clear responsibilities:
| Agent | Role | Mode | Permissions |
|-------|------|------|-------------|
| Spec | Clarifies vague stories into testable specs before design | Primary | Read-only, no bash |
| Architect | Designs system architecture, produces structured design decisions | Primary | Work-folder artifact writes + mkdir -p .path/work/* |
| Developer | Implements code changes end-to-end | Primary | Broad application edit: allow + risk-based bash policy |
| Auditor | Audits existing work for failures, risks, and gaps | Primary | Read-only + narrow proactive append-only audit notes for explicit work folders |
| Research | Researches documentation, APIs, SDK behavior, and best practices | Primary | Read-only, no bash |
| Reviewer | Reviews code changes, returns PASS/FAIL verdict | Subagent | Read-only + inspection commands + confirmation for project-specific validation |
| Explore | Fast codebase exploration | Subagent (built-in) | Read-only |
Key Design Principles
- Blast Radius Minimization: Only Developer modifies application code broadly. Architect can create/write handoff artifacts, Reviewer is strictly read-only, and Auditor may only append narrow audit notes when auditing an explicit or clearly detectable work folder.
- Separation of Concerns: Clarify (Spec) → Design (Architect) → Implement (Developer) → Review (Reviewer). Research supports facts/docs when needed; Audit is optional and user-invoked.
- Cross-Session Planning: Architect produces self-contained cross-session artifacts under
.path/work/{feature-slug}/. - Granular Permissions: Risk-based bash policy for Developer; Reviewer is strictly read-only; Auditor is read-only for code with a narrow work-folder audit-note exception; Architect can only create work-folder directories under
.path/work/. - Model-Agnostic by Default: No models are hardcoded. Use
opencode-path modelsto configure models explicitly for each agent. - Stack Profiles via Opt-In Command: The CLI installs agnostic agent templates by default. Stack-specific permission profiles (test runners, linters, type checkers) are added separately via
opencode-path profiles, keeping the base install clean and technology-agnostic.
Quick start
# Install globally
npm install -g opencode-path
# Initialize into your project (guided setup)
opencode-path init
# Or initialize into global config
opencode-path init --globalinit is a transparent, declarative desired-state assistant for the selected scope. It shows the current managed agents, optional skills, and profiles, then reconciles the confirmed target against the current packaged definitions. Restart opencode only when the result reports an actual configuration-time change.
Commands
init
Initialize or reconcile the workflow pack with a guided setup: scope → agents → optional skills → Graphify boundary → profiles → models → consolidated summary → confirm.
opencode-path init [options]Options:
| Flag | Description |
|------|-------------|
| --global | Use global scope (~/.config/opencode/) |
| --project | Use project scope (.opencode/) |
| --dry-run | Run the full selection flow, show the planned summary, and exit without writing |
| -y, --yes | Reconcile the installed managed state without selection prompts, inferred removals, or surprise optional/Graphify installs |
Behavior:
- Validates all packaged agent, skill, and profile templates before prompting.
- Resolves project/global scope and discovers active, missing, hidden, managed, and conflicting state.
- Agents — active managed agents are pre-selected. Choose a target set to retain/create/remove; explicitly unchecked managed custom agents are removed and unchecked built-ins are hidden. Choose Skip for now to preserve the current activation state instead of selecting an empty target.
- Optional skills — installed managed optional skills are pre-selected. Explicitly unchecked skills are removed; Skip for now preserves installed and missing state. Core skills remain mandatory and are never removable through
init. - Profiles — current profiles are preselected, and mixed state is disclosed for patchable agents (
developer,reviewer,auditor). Managing profiles applies one confirmed target set to selected agents; skipping preserves each agent's recognized set. Profile blocks are regenerated from current canonical definitions. - Models — valid installed models are preserved unless explicitly changed. Custom-agent models remain in frontmatter and built-in models remain in
opencode.json. - Every marked retained/selected custom agent and managed skill is compared with the latest packaged canonical definition. Replacements discard unsupported marked drift but preserve supported models and recognized profiles. Files without the managed marker are
Skipped conflictand are never adopted, overwritten, or deleted. - The aggregate preview lists exact paths and
Create,Replace,Remove,Unchanged, andSkipped conflictactions, with a visible replacement warning and one final confirmation. --yesuses installed managed state as the target, reconciles retained definitions and mandatory core skills, performs no inferred removals, and does not install missing optional or Graphify Explorer skills.- If no changes are planned,
initprintsNo changes needed.. Apply results distinguish completed, skipped, and failed paths; interrupted or failed applies disclose partial state and can be safely rerun.
Re-running init with the same target state is idempotent. Canonical definitions report Unchanged, profiles are not duplicated, and no restart is requested when no configuration-time content changed.
--dry-run runs the selection/planning flow and performs no writes, deletions, built-in hides/restores, model changes, or profile changes. This remains true with --yes; dry-run takes precedence.
Optional Graphify integration: init does not manage the Graphify CLI/library or Graphify's official skill. It may offer the existing explicit Graphify installation flow, or accept it with --with-graphify; --yes alone does not accept it. A managed graphify-explorer is reconciled only when already installed and marked. Missing or unmarked copies are not installed or adopted by normal reconciliation. Graphify hooks and automatic graph refresh are intentionally not installed.
graphify
Initialize or incrementally update the local Graphify repository graph using opencode-path's local/no-LLM code graphing defaults.
opencode-path graphify [options]Options:
| Flag | Description |
|------|-------------|
| --force | Force-update an existing graph (maps to graphify update . --force) |
Behavior:
- Verifies the Graphify CLI is available. If not, prints an actionable error directing you to run
opencode-path init --with-graphifyor install Graphify manually. - Prints that it is using local code graph mode with no LLM/API keys, and points semantic docs/media users to the direct Graphify CLI.
- If
graphify-out/graph.jsondoes not exist, runsgraphify . --code-onlyto initialize a new local code graph. - If
graphify-out/graph.jsonexists, runs Graphify's documented no-LLM code-file update command:graphify update .. - With
--forceand an existing graph, runsgraphify update . --force. With--forceand no graph, initializes normally. - After a successful init or update, attempts to write
.path/graphify-state.jsonwith freshness metadata: schema version, timestamp, Graphify mode, Graphify version, compatible install range, Git commit, and working tree dirty status. If the state file cannot be written (e.g. filesystem error), a warning is printed but the graph refresh is still considered successful. - Does not install hooks, create branches, create worktrees, or modify
.path/work.
opencode-path graphify intentionally does not expose semantic/full extraction flags, backend selection, API-key prompts, or arbitrary Graphify pass-through arguments. If you intentionally want Graphify to process docs, PDFs, images, video, or other media with its semantic extraction flow, run Graphify directly (for example, graphify .) and follow Graphify's own backend/API-key documentation.
Graphify freshness state (.path/graphify-state.json):
After a successful opencode-path graphify run, a .path/graphify-state.json file is written as advisory metadata. The state file is valid JSON with the following fields:
| Field | Description |
|-------|-------------|
| schemaVersion | Schema version (1) |
| updatedAt | ISO 8601 timestamp of the refresh |
| graphifyMode | Mode used by opencode-path (currently "local-code") |
| graphifyVersion | Parsed semantic version string (e.g. "0.9.11") or null |
| graphifyVersionRaw | Raw graphify --version output or null |
| graphifyCompatibleRange | Compatible install range (currently >=0.9.0,<0.10.0) |
| commit | HEAD commit hash at refresh time, or null when Git is unavailable |
| workingTreeDirty | true/false when Git status is available, or null when unavailable |
The state file is advisory — it helps Explorer judge graph freshness without automatically rebuilding the graph. It is written to .path/graphify-state.json relative to the repo root. Whether to track this file in Git (or ignore it) is left to your repo's policy.
Graphify installation and compatible version range:
- New Graphify CLI installs (via
init --with-graphify) useuv tool install graphifyy>=0.9.0,<0.10.0— the compatible0.9.xrelease line. - Existing Graphify CLI installations are not automatically reinstalled, downgraded, or upgraded. If you already have Graphify installed through any method (
uv tool install,pip, etc.), it will be used as-is. - Graphify is and remains optional. No agent workflow requires it.
Default behavior:
- Graphify hooks, background/watch refresh, and automatic graph rebuilds on Explorer use are not installed or enabled by default.
opencode-path graphifyis local/no-LLM by default: initial graph creation uses Graphify's explicit code-only extraction, and existing graph refresh uses Graphify's documented no-LLM code update path. opencode-path does not request API keys, consume LLM tokens, or send repository content to external LLM providers.- Explorer may use
.path/graphify-state.jsonmetadata as a freshness hint during medium/large reconnaissance, but it will not auto-refresh the graph. - When closing a feature, Developer may suggest running
opencode-path graphifybefore commits if.path/graphify-state.jsonexists — skipping the refresh is always valid.
agents
Manage which workflow agents are active: install, delete, hide, or restore.
opencode-path agents [options]Options:
| Flag | Description |
|------|-------------|
| --global | Use global scope |
| --project | Use project scope |
| --dry-run | Show planned changes without applying |
| -y, --yes | Skip the confirmation prompt |
Behavior:
- Resolves scope and displays agent directory and config paths.
- Shows a checkbox multi-select of all managed agents (custom + built-ins) with status glyphs:
●active,○missing,◌hidden,✕conflict. - Checked agents will be active. Unchecked custom agents are deleted. Unchecked built-ins are hidden via config.
- Conflict agents (manual files without the managed marker) are displayed but not modifiable.
- Shows planned changes. In
--dry-runmode, exits without writing. - Asks for confirmation (skipped by
--yes), then applies changes.
| Operation | Custom agent | Built-in agent (plan, build, explore) |
|-----------|-------------|--------------------------------------|
| Activate | Install .md file from template | Remove disable: true from config |
| Deactivate | Delete .md file | Set disable: true in config |
skills
Manage optional workflow skills in the selected project or global scope.
opencode-path skills [options]Options:
| Flag | Description |
|------|-------------|
| --global | Use global scope |
| --project | Use project scope |
| --dry-run | Show planned changes without applying |
| -y, --yes | Skip the confirmation prompt |
Behavior:
- Resolves scope and displays the selected target paths.
- Validates all skill templates before prompting. Malformed templates stop the command without applying changes.
- Shows optional managed skills in a checkbox multi-select with status glyphs:
●active,○missing,✕conflict. - Checked optional skills will be installed if missing. Unchecked active optional skills will be removed if they are managed by opencode-path.
- Core skills are shown informationally and cannot be removed by this command.
- Conflict skills are manual files without the managed marker. They are displayed but disabled and are not overwritten, modified, or deleted.
- Shows planned changes. In
--dry-runmode, exits without writing. - Asks for confirmation (skipped by
--yes), then applies installs/removals and prints a restart reminder.
Like managed agents, managed skills use the hidden marker (<!-- managed-by: opencode-path -->) so the CLI can distinguish its own files from manual files.
models
Configure model IDs for active managed agents.
opencode-path models [options]Options:
| Flag | Description |
|------|-------------|
| --global | Use global scope |
| --project | Use project scope |
Behavior:
- Resolves scope. Shows a spinner while loading models from
opencode models. - Shows a select menu to choose an agent or "Set all active agents to the same model".
- For each agent, shows available models (from OpenCode) plus "Custom model...".
- Custom agents store models in frontmatter. Built-in agents store models in
opencode.json. - After configuring, asks whether to configure another agent.
| Agent | Model stored in |
|-------|----------------|
| spec, architect, developer, auditor, reviewer, research | Agent .md file frontmatter model: field |
| plan, build, explore | opencode.json agent.<name>.model field |
Model IDs should use provider/model-id format (e.g., anthropic/claude-sonnet-4-6).
profiles
Apply stack-specific permission profiles to installed agents.
opencode-path profiles [options]Options:
| Flag | Description |
|------|-------------|
| --global | Use global scope |
| --project | Use project scope |
| --dry-run | Show planned changes without applying |
| -y, --yes | Skip the confirmation prompt |
Behavior:
- Resolves scope. Checks for active patchable agents (
developer,reviewer,auditor). - If no patchable agents are active, shows a warning and exits.
- Shows a checkbox multi-select of available profiles plus "All stacks".
- Profiles are inserted at the profile marker line in agent files using idempotency markers.
- In
--dry-runmode, exits without writing.
Available profiles:
| Profile | Validation commands | |---------|-------------------| | JavaScript / TypeScript | npm test, pnpm lint, npx jest, npx vitest, npx eslint, npx prettier --check, etc. | | Python | pytest, ruff check, mypy, pyright | | Go | go test, go vet (+ go fmt as "ask" for Developer) | | Rust | cargo test, cargo check, cargo clippy, cargo fmt --check (+ cargo fmt as "ask" for Developer) | | Swift | swift test, swift format lint (+ swift build, swift format as "ask" for Developer) | | Java / Kotlin | ./gradlew test, ./gradlew check, gradle test, mvn test | | Ruby | bundle exec rspec, bundle exec rubocop | | PHP | composer test, vendor/bin/phpunit, vendor/bin/phpstan |
Role-specific behavior: Developer receives the full profile including controlled mutating commands (listed as "ask"). Auditor and Reviewer receive only the read-only validation subset.
uninstall
Remove managed custom agent files. All config entries are preserved.
opencode-path uninstall [options]Options:
| Flag | Description |
|------|-------------|
| --global | Use global scope |
| --project | Use project scope |
| -y, --yes | Skip the confirmation prompt |
Behavior:
- Resolves scope and scans the agent directory.
- Identifies managed custom agent files (containing the managed marker) for deletion.
- Identifies unmarked files — these are skipped and never deleted.
- Shows the planned removals and asks for confirmation (skipped by
--yes). - Removes managed files and preserves
opencode.json, all config entries, and all unmarked files.
What is removed:
- Custom agent
.mdfiles that contain<!-- managed-by: opencode-path -->
What is preserved:
opencode.jsonitself (never deleted)- Unmarked custom agent files
- All built-in agent config entries (
agent.<name>.disable,agent.<name>.model, etc.) — these are preserved because the CLI cannot distinguish user-set entries from opencode-path-set entries - Any non-managed config fields
Note: If opencode-path previously hid a built-in agent (by setting
agent.<name>.disable: true), uninstall will not restore it. Runopencode-path agentsto restore hidden built-in agents before uninstalling if desired.
Concepts
Managed agents
The workflow pack manages a catalog of agents:
| Agent | Kind | Role | |-------|------|------| | spec | custom | Requirements clarification | | architect | custom | System design | | developer | custom | Implementation | | reviewer | custom | Code review (subagent) | | auditor | custom | Audit and verification | | research | custom | Documentation research | | plan | built-in | Planning (native to opencode) | | build | built-in | Build orchestration (native to opencode) | | explore | built-in | Codebase exploration (native to opencode) |
Custom agents are installed as .md files in the agent directory with a hidden marker (<!-- managed-by: opencode-path -->). The marker lets the CLI distinguish workflow-managed files from manual files.
Built-in agents (plan, build, explore) are native to opencode. They are active by default. opencode-path manages their visibility (hide/restore) and model configuration via opencode.json.
Scopes
Commands accept --global or --project to select the installation target:
- Project (
.opencode/): per-project agents and config - Global (
~/.config/opencode/): shared across all projects
If neither flag is passed and the terminal is interactive, a scope selection prompt appears. If both flags are passed, the command exits with a usage error. In non-interactive mode, one of the flags is required.
Conflict detection
If a file exists at a managed agent path without the managed marker, it is a conflict. Conflicts are displayed but never overwritten, deleted, or modified. To resolve:
- If the file was installed by a previous version of opencode-path: add the managed marker to the end of the file.
- If it is your own custom agent: leave it as-is.
- If you want to replace it: delete the file manually and re-run
initoragents.
Stack profiles
Profiles add stack-specific test runners, linters, and type checkers to agent permission blocks. They are applied at a designated marker line in agent files using idempotency markers (BEGIN/END blocks), so re-running the command does not duplicate entries.
Profiles have two variants per stack:
- Developer: full profile including controlled mutating commands (formatters, builds) listed as
ask - Auditor/Reviewer: read-only validation subset only
Exit codes
| Code | Meaning |
|------|---------|
| 0 | Success or no-op |
| 1 | Generic error |
| 2 | Usage error (e.g., --global --project together, or missing scope in non-interactive mode) |
| 130 | Canceled (Ctrl+C or ← Cancel) |
Cancellation
Select and checkbox prompts expose a visible "← Cancel" option. Confirmation prompts and free-text input prompts are canceled with Ctrl+C. init is the exception: its final confirmation and the custom-model format confirmation expose a visible "← Cancel" option. A second Ctrl+C forces immediate exit. No stack traces are printed on cancellation.
Troubleshooting
opencode not found in PATH
The models command runs opencode models to discover available model IDs. If opencode is not installed or not in your PATH:
Could not read models from opencode. Falling back to manual input.Fix: Install opencode and ensure it is in your PATH. You can still configure models manually using "Custom model..." in the prompt.
opencode models returns an empty list
If the opencode models command runs but returns no output, the models command falls back to manual input. This can happen if:
- No providers are configured in opencode
- API keys are not set for any provider
- The opencode installation is incomplete
Fix: Configure at least one provider in your opencode config and set the required API keys.
Restart reminder
When a command changes configuration-time managed definitions or built-in visibility, you must restart opencode for changes to take effect. init prints the reminder only after an actual successful create, replacement, removal, hide/restore, model/config, or Graphify Explorer change (including partial success); no-op, rejection, dry-run, and conflicts-only runs explicitly state that no restart is required. Each restart-requiring command prints:
⚠️ Restart opencode to apply changes.Managed marker conflicts
If init or agents shows a conflict, a file exists at the agent path without the managed marker. The CLI will not modify it.
Fix options:
- Add the managed marker to the end of the file:
<!-- managed-by: opencode-path --> - Delete the file manually and re-run
opencode-path initoropencode-path agents - Leave it as-is if it is your own custom agent
Complete uninstall
To fully remove all opencode-path managed files:
opencode-path uninstall --project # or --globalThis removes managed custom agent files. It does not delete opencode.json, unmarked files, or any built-in agent config entries (disable, model).
To remove both project and global installations:
opencode-path uninstall --project
opencode-path uninstall --globalTo also restore hidden built-in agents before uninstalling:
opencode-path agents --project # restore built-ins first
opencode-path uninstall --projectIf you need to manually clean built-in agent config entries after uninstall, edit opencode.json directly and remove the agent.<name>.disable or agent.<name>.model fields.
Hidden vs deleted agents
- Built-in agents (plan, build, explore) are hidden by setting
agent.<name>.disable: trueinopencode.json. Their model and other config fields are preserved. Restoring them removes thedisableflag. Theuninstallcommand does not touch built-in agent config — useopencode-path agentsto restore hidden built-ins before uninstalling. - Custom agents are deleted by removing their
.mdfile. The model (stored in the file's frontmatter) is lost. Reinstall withopencode-path initoropencode-path agents.
Non-interactive usage
In CI or scripts, pass --global or --project explicitly. Without an explicit scope in non-interactive mode, commands exit with code 2:
Non-interactive mode requires --global or --project.Contributing
Contributions welcome! See the repository for issues and development setup.
# Development
npm install
npm run build
npm test
npm run typecheckLicense
MIT
