Skip to content

cwp serve

shipped 1.0.0
cwp serve [flags]

Local only: it acts on no environment.

A conduit: standard output belongs to the program you run, so there is no --json, and cwp forwards the exit code unchanged.

FlagWhat it doesDefault
--allow-writes <stage>let cwp_apply run plans for environments in this stage; only build is accepted

Plus the shared flags -v, --verbose, -q, --quiet and --dry-run.

What it does

Speaks MCP over stdio, one tool per runnable command, so an agent works through cwp instead of around it. A tool takes the command’s arguments and flags as its input, and answers with the JSON envelope the command writes under --json. The tools come from the same manifest as the command pages, so a flag a tool takes is a flag the binary has.

A write answers with the plan, not the deed. cwp_push, cwp_db_pull, cwp_config_set and every other tool that changes something runs its command under --dry-run and hands back the plan with an id:

{ "plan": "3f2a9c1e7b04", "apply": "cwp_apply { \"plan\": \"3f2a9c1e7b04\" }", "envelope": { … } }

cwp_apply runs it. cwp makes the plan again first and refuses one whose steps changed since. What runs is what you saw.

Applying is bound to the stage. cwp serve --allow-writes build lets cwp_apply run plans for the local site and for environments in build. Without the flag there is no apply at all. An environment in launch, live or handover takes no write through this door, whatever flag you passed:

"prod" is live; a write there is applied by a person, not through cwp serve. The plan stands: cwp push prod

The key a guard reads is not a value this door sets. cwp_config_set hands back a plan for any settable key, and cwp_apply runs it. Two keys are the exception: environments.<env>.stage and defaults.backup_before_push. The first is what the server reads before it applies, the second is what the guard ladder reads before an upward write. A stage moved to build through the server would open the next apply. A person sets those two with cwp config set:

"environments.prod.stage" says where an environment stands, and cwp serve reads the stage before it applies; a person sets it, not cwp serve. The plan stands: cwp config set environments.prod.stage build

The read tools, cwp_doctor, cwp_status, cwp_coverage, cwp_log, cwp_config_get and the status tools, run as they are.

cwp serve                         # plans only
cwp serve --allow-writes build    # and cwp_apply for the local site and build environments

In Claude Code, from the project directory:

claude mcp add cwp -- cwp serve --allow-writes build

What it does not do

  • It does not open live. --allow-writes live is refused; the flag accepts build and nothing else (ADR-034).
  • It does not serve the conduits. cwp wp, cwp shell and cwp tail hand a terminal to another program; cwp init asks questions; cwp open opens a browser. None of them is a tool.
  • It does not listen on the network. Stdio only: whoever started the process is the user, and there is no token to leak.

TODO