mcp-code-worker is a local controlled execution layer for coding hosts such as Codex. It exposes CLI and MCP tools that let a host delegate narrow work to registered model workers while keeping repository context, deterministic validation, task artifacts, and patch gates explicit and auditable.
cw is intended to sit underneath an existing coding host, not replace it. The host keeps user intent and final judgment; cw provides the controlled runtime for model-worker routing, repository context packs, validation, local artifacts, and reviewable patch lifecycle gates.
Use it when you want a coding host to delegate scoped tasks to one or more registered workers without giving those workers direct, unchecked control over your repository.
- A local CLI and MCP server for host-managed coding workflows
- A worker registry and routing layer for API-model workers
- A repository-context, validation, artifact, and audit runtime
- A dry-run-first patch proposal and gated apply workflow
- A way to qualify worker models before assigning higher-risk coding tasks
- Not a Codex, OpenCode, Cursor, or Claude Code clone
- Not an interactive coding terminal or TUI
- Not a full chat interface
- Not a web UI product
In host-driven use cases such as Codex, cw stays as the controlled execution/runtime layer.
- The host agent stays responsible for user intent, final judgment, and acceptance.
cwprovides the controlled runtime: worker routing, repository context packs, deterministic validation, artifact persistence, and patch gates.- The recommended host-facing path is
cw_start_taskand other host-managed tools. - For narrow repo-grounded checks, prefer explicit file lists with strict file mode so CW fails fast instead of silently widening or skipping critical evidence.
Human / Coding Agent / CI / MCP Client
|
v
cw CLI / MCP
|
v
Orchestration Runtime Layer
| | \
v v v
Worker Routing Deterministic Tools CW Storage / Artifacts
|
v
Worker Models / Local Clients
packages/
core/
models/
graph/
tools/
mcp-server/
cli/
apps/
playground/
examples/
host-worker-basic/
docs/
- Node.js
22.13.0+ - pnpm
>=10
This repository requires Node.js 22.13.0 or newer. CI currently pins 22.13.0 as the minimum validated baseline.
See docs/supported-matrix.md for the explicit OS, Node.js, and MCP host support boundary.
For MCP hosts, the current release-validated integration is Codex. OpenCode, Claude Code / Claude Desktop, Cursor, and VS Code snippets are untested scaffolding unless the supported matrix says otherwise.
Global npm install:
npm i -g mcp-code-worker
cw init
cw doctor
cw mcp list-toolsDevelopment checkout:
node --version
pnpm install
pnpm build
pnpm exec cw doctor
pnpm exec cw init
pnpm exec cw doctor
pnpm typecheck
pnpm testcw init
cw doctor --probe
cw mcp configUse cw init as the default first-run bootstrap path. Run it interactively by default. For scripted setup, pass the worker fields explicitly, for example cw init --worker-id=deepseek-flash --worker-provider=openai-compatible --worker-model=deepseek-v4-flash --worker-base-url=https://api.deepseek.com --register-worker --allow-write, then store credentials with cw auth login.
Minimal hosted-model flow:
cw init
cw worker registry add --worker=deepseek-pro --provider=openai-compatible --model=deepseek-v4-pro --base-url=https://api.deepseek.com --allow-write
cw auth login --worker=deepseek-pro
cw doctor --probe --worker=deepseek-pro
cw worker evaluate --suite=smoke --worker=deepseek-pro --save
cw task start --goal="Review this repository" --worker=deepseek-pro --allow-write-sessionFor the step-by-step guide, including Codex MCP restart guidance, notes about untested MCP hosts such as OpenCode/Qoder/Trae, model-specific notes, current GLM support status, and the latest compatibility test list, see docs/usage.md.
Public installation and MCP launch guidance lives in docs/install.md. The current official internal distribution shape is documented in docs/distribution.md.
Unless noted otherwise, read every cw ... example below as the public npm-installed CLI. In a repository checkout, use pnpm exec cw ... from the repository root instead.
Legacy repository-local .cw/ directories are unsupported and ignored by current builds.
cw init writes user-scoped CW workspace storage under ~/.code-worker/<workspace-id>/ by default:
config.jsondata.db
config.json keeps editable worker definitions and runtime defaults. data.db
is the SQLite store for worker secrets, worker profiles, latest coding evaluation
records per worker and suite, worker execution records, task sessions, task
artifacts, and audit events.
Current release-grade worker support is API-model first. Local client adapters
such as client, opencode, claudecode, and codex remain in the codebase
as experimental compatibility scaffolding, but they are not part of the current
npm/e2e-supported worker path.
cw task start --goal="Fix failing typecheck" --scope=packages/core --worker=qwen-local --typecheck --error-log-file=./tmp/tsc-error.log --run-fix --allow-write-session
cw task resume <taskId>
cw task report <taskId>
cw auth login --worker=qwen-local
cw auth list
cw auth logout --worker=qwen-local --allow-write
cw cleanup runs
cw cleanup audit
cw model list
cw mcp config
cw mcp serve
cw mcp list-toolscw model list shows configured worker models resolved from config, environment, and defaults. It is not the worker inventory; use cw worker profile list for persisted capability profiles.
For normal coding work, prefer cw task start, cw task resume, and cw task report. Lower-level cw review ..., cw validate, cw fix error, and cw patch ... commands remain available as advanced/debug surfaces when you need tighter control or smaller workflow building blocks.
cw review files --strict-files and cw_run_host_worker expose debug evidence for host-managed worker runs, including requested files, selected files, worker metadata, worker trust profile, worker execution record id, structured-output mode, repair attempts, failure kind, and semantic rejection details.
Workers are not treated as automatically qualified just because a model endpoint exists.
Warning: A weaker worker model does not automatically save tokens. If the host still has to verify, rewrite, or redo most of the output, the total token cost can increase rather than decrease. Token savings are more likely when the delegated task is narrow, mechanical, low-risk, and easy to verify, such as running checks, extracting fields, collecting logs, or summarizing a very small scoped input.
Use cw init as the default first-run path. After workspace bootstrap is already done, use cw worker onboard --worker=<workerId> --allow-write only when you need to rerun or recheck one named worker without repeating workspace setup, or register a named worker and evaluate it before assigning real work:
cw worker registry add \
--worker=qwen-local \
--provider=litellm \
--model=qwen3-coder \
--base-url=http://localhost:4000/v1 \
--allow-write
cw auth login --worker=qwen-local
cw worker evaluate --suite=smoke --worker=qwen-local --save
cw worker profile list
cw worker profile get qwen-localThe smoke evaluation workflow evaluates:
- instruction following
- structured JSON output
- strict scope discipline
- summarization
- evidence-linked repository review
- refusal when mandatory evidence is missing
- code understanding
- simple TypeScript code generation
- confidence calibration
Smoke Evaluation results produce a WorkerCapabilityProfile that affects routing:
qualified: worker can receive the task types it qualified fornot-qualified: worker completed evaluation but stays restricted from qualified task types
Example warning output:
Worker qwen-local failed onboarding evaluation.
Status: not-qualified
Reasons:
- structured-output: Output failed schema validation.
- codegen: Generated code uses any.
- confidence-calibration: Worker reported high confidence on an ambiguous task.
Recommended action:
- Do not assign codegen tasks.
- Limit this worker to qualified low-risk tasks.
- Require host review for every accepted output.
If the worker cannot complete evaluation because of configuration or connectivity problems, the smoke evaluation result is not persisted and production routing should treat the worker as unavailable until the runtime issue is fixed.
Use --save if you want to persist the smoke evaluation result:
cw worker evaluate --suite=smoke --worker=qwen-local --saveSaved profiles are written to the SQLite workspace store at:
~/.code-worker/<workspace-id>/data.db#worker_profiles
You can inspect persisted profiles with:
cw worker profile list
cw worker profile get qwen-localCurrent behavior is trust-aware rather than endpoint-trusting: persisted profiles, smoke evaluations, and coding evaluations influence the worker trust profile, recommended mode, warnings, and patch-generation eligibility. Missing or stale evidence should push exploratory work toward dry-run or host-review mode instead of silently accepting a worker result.
Register a reusable worker, evaluate it, and keep the assignment explicit:
cw worker registry add \
--worker=qwen-local \
--provider=litellm \
--model=qwen3-coder \
--base-url=http://localhost:4000/v1 \
--allow-write
cw worker evaluate --suite=smoke --worker=qwen-local --save
cw auth login --worker=qwen-local
cw task start \
--goal "Review this repository" \
--worker=qwen-local \
--require-profile
cw audit listThis flow keeps worker selection local, auditable, and gated by a persisted capability profile while leaving the host in control of the overall task.
Use cw task start and cw task resume for day-to-day engineering checks. The commands below are still available when you intentionally want lower-level review building blocks:
cw review repo --worker=qwen-local --scope=packages/graph
cw review diff --worker=qwen-local --base=main --head=HEAD
cw review files --worker=qwen-local --file=packages/graph/src/index.ts
cw validate --all
cw validate --all --stop-on-failure --execute
cw fix error --worker=qwen-local --error-log-file=./tmp/tsc-error.log --scope=packages/coreThese commands build repository context packs, read scoped files safely, and route deterministic validation into the review output.
For the default user path, prefer cw task start and cw task resume so review, validation, patch proposal, and patch application stay in one host-managed workflow. Patch handling is still available as explicit advanced stages when you need to inspect each step yourself:
cw fix error --worker=qwen-local --error-log-file=./tmp/tsc.log --scope=packages/core
cw patch propose \
--goal "Fix failing typecheck" \
--scope=packages/core \
--worker=qwen-local
cw patch inspect ./tmp/candidate.patch
cw patch apply ./tmp/candidate.patch --dry-run
cw patch apply ./tmp/candidate.patch \
--allow-write \
--confirm-apply \
--typecheck \
--lint \
--testSafety constraints for patch lifecycle:
- Dry-run is the default.
- Applying a patch requires both an explicit write gate and an explicit confirmation gate.
- No command creates commits or PRs automatically.
- Patch actions emit audit events.
- Validation can run after apply, but failed validation does not auto-revert in this iteration.
Task sessions keep local review artifacts and resumable state in SQLite under ~/.code-worker/<workspace-id>/data.db by default:
cw task start \
--goal "Fix failing typecheck in packages/core" \
--scope=packages/core \
--worker=qwen-local \
--require-profile \
--typecheck \
--lint \
--propose-patch \
--allow-write-session
cw task status <taskId>
cw task resume <taskId>
cw task report <taskId>Patch apply is still a separate explicit gate even inside task resume:
cw task resume <taskId> \
--apply-patch \
--allow-write \
--confirm-applySession persistence is separate from repository writes. --allow-write-session only permits CW-managed session persistence in data.db. It does not enable patch apply.
If you resume an already persisted task session without --allow-write-session, the original stored session remains readable and resumable. Only the new resume output stays temporary and is not written back into CW-managed storage.
See docs/permissions.md for the full write-gate model.
Start the stdio server:
cw mcp servePrint a generic stdio config snippet for local MCP clients:
cw mcp configList exposed tool names:
cw mcp list-toolscw_run_host_worker can return permission_required when a worker asks the
host to run a scoped tool request that needs user approval. The response includes
a short-lived continuationToken:
{
"status": "permission_required",
"permissionRequest": {
"continuationToken": {
"taskId": "task-123",
"requestId": "tool-req-456",
"expiresAt": "2026-07-02T10:30:00.000Z"
},
"request": {
"id": "tool-req-456",
"action": "read_file_snippet",
"path": "package.json"
}
}
}After the user approves or denies the request, call cw_run_host_worker again
with the same continuationToken and a matching userPermissionGrants entry:
{
"goal": "Review root scripts",
"taskType": "review-lite",
"scope": "packages/core",
"workerId": "default-worker",
"continuationToken": {
"taskId": "task-123",
"requestId": "tool-req-456",
"expiresAt": "2026-07-02T10:30:00.000Z"
},
"userPermissionGrants": [
{
"id": "grant-1",
"taskId": "task-123",
"requestId": "tool-req-456",
"action": "read_file_snippet",
"grantScope": "once",
"granted": true,
"status": "granted",
"decidedAt": "2026-07-02T10:20:00.000Z"
}
]
}The token is a continuation window for this specific pending request, not a
long-term permission. It currently expires after 15 minutes. User grants must
match the token's taskId and requestId, and the host also checks the grant
action, status, and optional grant expiration before executing the tool request.
See .env.example.
Supported environment variables are limited to process identity diagnostics:
MCP_SERVER_NAMEMCP_SERVER_VERSIONLOG_LEVEL
Runtime configuration resolves in this order:
- CLI flags
~/.code-worker/<workspace-id>/config.json- built-in defaults
Use config.json as the primary home for persisted worker, validation, safety, and MCP-adjacent runtime defaults. Worker API keys are managed only through cw auth login, cw auth list, and cw auth logout, and are persisted in the workspace SQLite store. Writing API keys into config.json is unsupported and should be treated as invalid operator behavior. Local client command fields remain in config.json.workers[] only as experimental compatibility settings for future local-adapter support. Launch cw from the intended workspace root, and never commit real keys or include them in logs.
Repository context settings in the user-scoped CW config.json control default ignoredPaths and strictFiles behavior for review, fix, patch, and task workflows.
host-worker-workflow: runs one explicit worker task under host control with answer-quality gatesreview-workflow: summarizes diff impact, risks, missing tests, and follow-up itemsfix-error-workflow: analyzes error logs and proposes safe validation-oriented fix stepspatch-proposal-workflow: generates and inspects patch proposals without applying repository writestask-session-workflow: runs the end-to-end persisted task pipelineworker-smoke-evaluation-workflow: evaluates a worker model before production routing and generates a capability profile
Run pnpm exec tsx examples/host-worker-basic/src/index.ts to inspect the host-managed example workflow.
- Add a worker class under
packages/graph/src/workers. - Give it a clear
WorkerCapabilitywith Zod-backed schemas. - Declare the worker's supported task types so routing can enforce capability limits.
- Route it from a workflow and keep its output reviewable.
- Make sure onboarding smoke evaluation results can constrain how it is assigned.
- Add tests for the workflow path it affects.
- Create a workflow file under
packages/graph/src/workflows. - Use LangGraph.js to model transitions explicitly.
- Reuse core contracts and host-managed quality gates.
- Expose it through the CLI or MCP only after tests exist.
- Add a tool definition in
packages/mcp-server/src/tools. - Keep the handler thin and delegate to core workflow APIs.
- Register it in
packages/mcp-server/src/server.ts. - Add a registration test.
Persist the non-secret worker settings in config.json, for example:
{
"version": 1,
"workers": [
{
"workerId": "litellm-main",
"provider": "litellm",
"model": "<model>",
"baseURL": "https://litellm.example.com",
"enabled": true,
"tags": [],
"createdAt": "2026-07-01T00:00:00.000Z",
"updatedAt": "2026-07-01T00:00:00.000Z"
}
]
}Store the matching credential separately:
cw auth login --worker=litellm-main- Default mode is dry-run.
- File writes require explicit policy allowance.
- Shell execution is allowlisted.
- Read-only git inspection commands such as
git diffcan still execute inside dry-run so review workflows keep working without enabling writes. cw init,cw cleanup, worker registry writes, and task session persistence remain local-only inside CW-managed storage.- Worker execution records are local CW storage records and remain dry-run until the execution context permits managed storage writes.
- Repository reads stay inside the repo root and block secret-like files such as
.envand private keys. - Dedicated review and fix flows return structured JSON and do not apply patches.
- Patch proposal, inspection, and apply are separated to keep write actions reviewable.
- If structured patch generation fails, the fallback proposal is marked as a blocked
[PLACEHOLDER]artifact and cannot be applied. - If patch generation concludes that the scoped code already needs no repository change, CW now reports that result separately as
no-change-neededinstead of treating it as an ordinary blocked placeholder. - Validation commands go through the safe command path and can be inspected through audit logs.
cw audit listexposes the local audit trail for workflow, file, and command events.cw cleanup runsandcw cleanup auditonly delete local CW artifacts and never touch project source files.- In host-driven flows, worker outputs are not final until the host accepts them.
- Workers should have smoke or coding qualification evidence before higher-risk production tasks; missing evidence lowers trust and should require dry-run or host review.
- Workers that fail structured output or reliability checks become
not-qualified. Environment or configuration failures keep the worker unavailable for formal tasks until the runtime issue is fixed. - Worker secrets should be persisted only through
cw auth logininto the user-scoped CW SQLite store and should never be logged.
See docs/permissions.md for the concrete permission layers and write-gate examples.
Use fast checks while developing:
pnpm typecheck
pnpm test
pnpm smokepnpm test intentionally excludes the packed and dist smoke tests. Those tests
are slower and protect the npm delivery path rather than ordinary unit behavior.
Before publishing or shipping CLI/MCP packaging changes, run the release gate:
pnpm release:checkrelease:check runs the build plus both package-level smoke layers:
pnpm smoke:pack: builds the publish directory, packs it with npm, installs the tarball into a temporary prefix, and verifies the installedcwbin, storage initialization, and MCP tool listing.pnpm smoke:dist: verifies the built CLI entrypoint, repo bin shim, live MCP launch throughdoctor --mcp, and source/dist parity for selected commands.
- Expand workflow coverage and richer deterministic validations
- Add domain-specific orchestration packages later
- Add CI automation for checks and releases
- Keep the core focused on orchestration rather than UI