The full upstream README, mirrored here for reference. Install config, tool schemas, adoption signals, and an original overview live on the Nexus MCP listing page.
An MCP server that enables AI models to invoke AI CLI agents (Codex, Claude Code, OpenCode) as tools. Provides durable workspace-scoped jobs, parallel execution, automatic retries with exponential backoff, JSON-first response parsing, discoverable prompt templates, model tier classification, and persistent preferences through MCP tools, resources, and prompts.
Nexus MCP is useful whenever a task benefits from querying multiple AI agents in parallel rather than sequentially:
batch_prompt fans out tasks with asyncio.gather and a configurable
semaphore (default concurrency: 3)default (safe, no auto-approve), yolo (full auto-approve)list_prompts/get_prompt; each returns structured messages with expert framing the client can use or ignorenexus://runners resource includes tier data per modelbuild_command + parse_output, register in RunnerFactory| Agent | Status |
|---|---|
| Codex | Supported |
| Claude Code | Supported |
| OpenCode | Supported |
uvx installs the package in an ephemeral virtual environment and runs it — no cloning required.
To check the installed version:
To update to the latest version:
Claude Desktop (~/Library/Application Support/Claude/claude_desktop_config.json on macOS):
Cursor (.cursor/mcp.json in your project or ~/.cursor/mcp.json globally):
Claude Code (CLI):
Generic stdio config (any MCP-compatible client):
All env keys are optional — see Configuration for the full list.
Prerequisites:
Optional (for integration tests):
codex --versionclaude --versionopencode --versionClaude Code note: Nexus invokes Claude Code non-interactively via
claude -p. Anthropic saysclaude -pand Agent SDK usage draw from separate monthly Agent SDK credits starting 2026-06-15, while interactive Claude Code usage remains on plan usage limits: https://support.claude.com/en/articles/15036540-use-the-claude-agent-sdk-with-your-claude-plan
Note: Integration tests are optional. Unit tests run without CLI dependencies via subprocess mocking.
⚠️ Experimental — This integration has not been validated end-to-end by the maintainer. Expect rough edges in setup, auth, and tool exposure. The MCP tools surfaced from upstream OpenCode track the upstream project and may change without notice. Feedback and bug reports are welcome.
Run an isolated OpenCode server for HTTP-based agent execution alongside the CLI runner. Provides session management, file search, permissions, and 38 additional MCP tools when the server is healthy.
Quick start:
.env.example to .env and set PROJECT_DIR to your project path:
The server binds to 127.0.0.1 (localhost only) by default for security. See docs/opencode-server-setup.md for the full guide including remote access, multi-project setup, and network security.
Once nexus-mcp is configured in your MCP client, your AI assistant automatically sees its tools.
The reliable trigger is explicitly asking for output from an external AI agent (e.g. Codex, Claude Code, OpenCode).
Generic "do this in parallel" prompts may be handled by the host AI's own capabilities instead.
The cli parameter is optional — if omitted and the client supports MCP elicitation, the server will
ask which runner to use. The server provides runner metadata (names, models, availability,
execution modes) in its connection instructions — no discovery call needed. The cli parameter
includes a JSON schema enum listing valid runner names.
You say: "Get perspectives from Codex, Claude Code, and OpenCode on transformer architectures."
You say: "Have Codex, Claude Code, and OpenCode each review this diff in parallel."
You say: "Ask Codex to explain the difference between TCP and UDP."
You say: "Explain the CAP theorem using one of the available agents."
If the client supports MCP elicitation, the server asks which runner to use. Pass "elicit": false to skip.
You say: "Use YOLO mode with Codex from now on."
Subsequent calls inherit these settings. Preferences persist across MCP sessions until explicitly cleared.
Fallback chain: explicit parameter → saved preference → per-runner env → global env → hardcoded default.
Nexus exposes a durable agent_* surface and the original compatibility prompt surface. Every
durable tool requires an explicit workspace selector containing exactly one of an existing
workspace_id or a filesystem path; Nexus never infers a durable workspace from the server's
current directory. A path is resolved to one canonical workspace identity before admission.
Execution-starting durable tools return a JobHandle immediately. Clients use the observation and
control tools to follow the normalized job independently of an MCP request lifetime.
| Tool | Description |
|---|---|
agent_start | Create a durable session and queue its first turn |
agent_continue | Queue another turn on an existing session |
agent_fork | Create a child session when the backend supports forking |
agent_review | Queue a typed review operation on an existing session |
agent_diagnose | Queue a sessionless backend diagnostic job |
agent_status | Read the current normalized status of one job |
agent_result | Read the pending or terminal typed result of one job |
agent_list | Page through authorized jobs in one workspace |
agent_backends | List backend capabilities and current availability for one workspace |
agent_cancel | Request idempotent cancellation of a queued or active job |
agent_respond | Resolve a pending approval, permission, question, or form input |
The compatibility prompt and batch_prompt tools retain their background-task behavior. They
return FastMCP task IDs so clients can poll without holding a long-running MCP request open.
Per-call concurrency defaults to 3. The shared process runtime starts with 3 workers and grows to
a high-water maximum of 8; one call whose effective demand exceeds 8 is rejected explicitly,
while concurrent calls share the process ceiling and may queue.
| Tool | Task? | Description |
|---|---|---|
batch_prompt | Yes | Fan out prompts to multiple runners in parallel; returns MultiPromptResponse |
prompt | Yes | Single-runner convenience wrapper; routes to batch_prompt |
set_preferences | No | Set or selectively clear persistent defaults for execution mode, model, retries, timeouts, elicitation, and trigger suppression |
get_preferences | No | Retrieve current preferences |
clear_preferences | No | Reset all preferences |
set_model_tiers | No | Save model tier classifications (client sends sampling/benchmark results; server persists) |
get_model_tiers | No | Retrieve saved model tier classifications |
batch_prompt| Parameter | Required | Default | Description |
|---|---|---|---|
tasks | Yes | — | List of task objects (see below) |
max_concurrency | No | 3 | Max parallel agent invocations for this call; effective demand above the process worker maximum of 8 is rejected |
elicit | No | pref or true | Enable/disable interactive elicitation for this call |
Task object fields:
| Field | Required | Default | Description |
|---|---|---|---|
cli | No | — | Runner name (e.g. "codex"); if omitted, elicitation asks which runner to use |
prompt | Yes | — | Prompt text |
label | No | auto | Display label for results |
context | No | {} | Optional context metadata dict |
execution_mode | No | pref or "default" | "default" or "yolo" |
model | No | pref or CLI default | Model name override |
max_retries | No | pref or env default | Max retry attempts for transient errors |
output_limit | No | pref or env default | Max output bytes |
timeout | No | pref or env default | Subprocess timeout in seconds |
retry_base_delay | No | pref or env default | Base delay for exponential backoff |
retry_max_delay | No | pref or env default | Max delay cap for backoff |
Note:
elicitis a batch-level parameter. When enabled, the server runs a single upfront elicitation pass across all tasks rather than prompting per-task.
promptSame parameters as a single task object in batch_prompt, plus elicit (batch-level in batch_prompt, per-call here).
set_preferences| Parameter | Required | Default | Description |
|---|---|---|---|
execution_mode | No | — | "default" or "yolo" |
model | No | — | Model name (e.g. "gpt-5.2") |
max_retries | No | — | Max total attempts (≥1; 1 = no retries) |
output_limit | No | — | Max output bytes (≥1) |
timeout | No | — | Subprocess timeout seconds (≥1) |
retry_base_delay | No | — | Backoff base delay seconds (≥0) |
retry_max_delay | No | — | Backoff max delay seconds (≥0) |
elicit | No | true | Enable/disable elicitation |
confirm_yolo | No | true | Prompt before YOLO mode (auto-suppressed after first accept) |
confirm_vague_prompt | No | true | Prompt on very short prompts |
confirm_high_retries | No | true | Prompt when max_retries > 5 |
confirm_large_batch | No | true | Prompt when batch > 5 tasks |
clear_* | No | false | Clear any field individually (e.g. clear_model: true) |
get_preferences / clear_preferencesget_preferences — no parameters, returns all fields (null when unset).
clear_preferences — no parameters, resets all to null. Does not clear model tiers.
set_model_tiers| Parameter | Required | Default | Description |
|---|---|---|---|
tiers | Yes | — | Dict mapping model names to tiers ("quick", "standard", "thorough") |
Persists tier classifications. Clients typically call once via sampling or benchmark fetch.
get_model_tiersNo parameters. Returns saved tiers as dict[str, str], or {} if none saved.
| Operation | Tool | Notes |
|---|---|---|
| Set fields | set_preferences | Persists across sessions |
| Read values | get_preferences | null for unset fields |
| Clear all | clear_preferences | Does not clear model tiers |
| Clear one field | set_preferences with clear_*: true | Others preserved |
| Suppress elicitation | set_preferences with confirm_*: false | YOLO/batch/retry auto-suppress after accept |
| Re-enable prompt | set_preferences with clear_confirm_*: true | Resets to default |
| Save/read tiers | set_model_tiers / get_model_tiers | Persists across sessions |
The framework-independent core separates normalized domain contracts from concrete backends,
storage, and the MCP transport. A job is one admitted operation and owns its retry attempts,
events, controls, and terminal result. A session is a durable conversation identity bound to one
workspace and backend; agent_start creates it, agent_continue reuses it, and agent_fork
creates a child when supported. Diagnostic jobs may be sessionless. A session and a job are not MCP
client sessions or FastMCP background-task IDs.
Jobs and sessions use private | workspace access policies:
private (the default) is visible only to the owning principal.workspace is visible to the owner and to callers explicitly authorized for that same workspace.
It never grants cross-workspace access. For the local MCP adapter, the operating-system user is
the principal and the private database permissions form the trust boundary.The SQLite database contains sensitive prompts, normalized events, provider references, and
results. Set NEXUS_DB_PATH to override its location. Otherwise Nexus uses these per-user paths:
~/Library/Application Support/nexus-mcp/nexus.sqlite3%LOCALAPPDATA%\nexus-mcp\nexus.sqlite3 (falling back to
~/AppData/Local/nexus-mcp/nexus.sqlite3)${XDG_DATA_HOME:-~/.local/share}/nexus-mcp/nexus.sqlite3On POSIX systems Nexus removes group and other access from the database directory and SQLite files. Normalized job, session, event, and result records are retained indefinitely by default; Nexus does not schedule automatic pruning. Applying retention cutoffs is an explicit store operation, and no public MCP pruning tool is currently exposed.
Codex, Claude Code, and OpenCode execution currently passes through the temporary
LegacyRunnerBackend bridge while native backends are developed. The bridge supports normalized
turns only: it does not provide backend cancellation, graceful interruption, session forking, or
safe reconciliation after an interrupted attempt. These are legacy-backend limitations, not core
job-model promises; clients should inspect agent_backends capabilities before selecting an
operation.
Nexus MCP provides 10 discoverable prompt templates that clients can browse via list_prompts() and render via get_prompt(name, args). Each prompt returns structured messages with expert framing — the client decides how (or whether) to use them.
Design principle: Server informs, client decides. Prompts provide the scaffold (role, structure, methodology); the client decides runner, model, depth, and orchestration. Prompts are completely optional — existing prompt/batch_prompt tools work exactly as before.
| Prompt | Tags | Parameters | Purpose |
|---|---|---|---|
code_review | analysis | file, instructions | Structured code review with findings by severity |
debug | analysis | error, context, file | Systematic diagnosis: reproduce, isolate, root cause, fix |
quick_triage | analysis | description, file | Fast assessment: what's wrong, severity, next step |
research | analysis | topic, scope | Structured research with source citations |
second_opinion | analysis | original_output, question | Independent review of another AI's output |
implement_feature | generation | description, language, constraints | Feature implementation with quality checklist |
refactor | generation | file, goal, constraints | Behavior-preserving restructuring |
bulk_generate | generation | template, variables | Expand template across variable sets |
write_tests | testing | file, framework, coverage_goal | Test generation with configurable coverage approach |
compare_models | comparison | prompt, criteria | Multi-runner comparison framework |
Read-only data endpoints that clients query for runner metadata, configuration, and preferences.
| Resource URI | Description |
|---|---|
nexus://runners | All registered CLI runners with models (enriched with tier data), modes, availability |
nexus://runners/{cli} | Single runner details by name (URI template) |
nexus://config | Resolved operational config defaults (timeouts, retries, output limits) |
nexus://preferences | Current preferences with config fallback |
Models in nexus://runners include tier data: {"name": "gpt-5.4-mini", "tier": "quick"}. Tiers are quick (fast/cheap), standard (balanced), or thorough (max quality). Models with only heuristic tiers appear in unclassified_models — calling set_model_tiers moves them out.
Before set_model_tiers — all tiers are heuristic guesses, all models are unclassified:
After set_model_tiers — saved tiers replace heuristics, classified models leave the list:
| Variable | Default | Description |
|---|---|---|
NEXUS_DB_PATH | Platform per-user data directory | Durable SQLite job database; contains sensitive prompts and results |
NEXUS_OUTPUT_LIMIT_BYTES | 50000 | Max output size in bytes before temp-file spillover |
NEXUS_TIMEOUT_SECONDS | 600 | Subprocess timeout in seconds (10 minutes) |
NEXUS_TOOL_TIMEOUT_SECONDS | 900 | Tool-level timeout in seconds (15 minutes); set to 0 to disable |
NEXUS_RETRY_MAX_ATTEMPTS | 3 | Max attempts including the first (set to 1 to disable retries) |
NEXUS_RETRY_BASE_DELAY | 2.0 | Base seconds for exponential backoff |
NEXUS_RETRY_MAX_DELAY | 60.0 | Maximum seconds to wait between retries |
NEXUS_CLI_DETECTION_TIMEOUT | 30 | Timeout in seconds for CLI binary version detection at startup |
NEXUS_EXECUTION_MODE | default | Global execution mode (default or yolo) |
Pattern: NEXUS_{AGENT}_{KEY} (agent name uppercased). Per-runner values override global values.
Valid {AGENT} values: CLAUDE, CODEX, OPENCODE, OPENCODE_SERVER
| Variable pattern | Example | Description |
|---|---|---|
NEXUS_{AGENT}_MODEL | NEXUS_CODEX_MODEL=gpt-5.2 | Default model for this runner |
NEXUS_{AGENT}_MODELS | NEXUS_CODEX_MODELS=gpt-5.2,gpt-5.4-mini | Comma-separated model list (surfaced in server instructions) |
NEXUS_{AGENT}_TIMEOUT | NEXUS_CODEX_TIMEOUT=900 | Subprocess timeout override |
NEXUS_{AGENT}_OUTPUT_LIMIT | NEXUS_CODEX_OUTPUT_LIMIT=100000 | Output limit override |
NEXUS_{AGENT}_MAX_RETRIES | NEXUS_CLAUDE_MAX_RETRIES=5 | Max retry attempts override |
NEXUS_{AGENT}_RETRY_BASE_DELAY | NEXUS_CLAUDE_RETRY_BASE_DELAY=1.0 | Backoff base delay override |
NEXUS_{AGENT}_RETRY_MAX_DELAY | NEXUS_OPENCODE_RETRY_MAX_DELAY=30.0 | Backoff max delay override |
NEXUS_{AGENT}_EXECUTION_MODE | NEXUS_CODEX_EXECUTION_MODE=yolo | Execution mode override |
Invalid per-runner values are silently ignored (the global or hardcoded default is used instead).
This project follows Test-Driven Development (TDD) with strict Red→Green→Refactor cycles.
Test markers:
@pytest.mark.integration — requires real CLI installations@pytest.mark.slow — tests taking >1 secondAll quality checks run automatically via pre-commit hooks. Run manually:
pyproject.toml → [tool.ruff]pyproject.toml → [tool.mypy]asyncio_mode = "auto", no @pytest.mark.asyncio needed — pyproject.toml → [tool.pytest.ini_options].pre-commit-config.yamltype keyword for type aliases: type AgentName = strstr | None (not Optional[str])match statements for complex conditionalsfrom __future__ import annotationsStable releases are cut by running the Tag Release workflow from the Actions
tab and choosing a bump (auto infers it from Conventional Commits since the
last tag). Pre-releases are tagged manually. See RELEASE.md for
the full maintainer workflow, recovery steps, and notes on server.json
placeholder fields.
MIT