MCP support (#140)

Publish Nexus's control plane as an MCP server, so Claude — on a phone, on the desktop, or inside another Nexus worker — can open sessions, message them, tear them down, and answer "is anything waiting on me?" without opening the web UI.

Tracks docs/superpowers/specs/2026-09-15-mcp-server-design.md (issue #140).

Shape

Nexus is an OAuth 2.0 resource server; an embedded but pluggable OAuth 2.1 authorization server issues the tokens. One instance setting drives both the advertised issuer and the active verifier, so they cannot disagree — point it at an external IdP and the authorization server simply isn't mounted.

Phone access requires OAuth, not a bearer token: static_headers is Beta and org-admin-only. Nexus is already public at a.lck.sh behind TLS, so there is no exposure work.

Sequence

Prerequisites — independent of MCP, shippable now:

  1. Migrate to zod v4 (the SDK needs it)
  2. Rate-limit /api/auth/unlock (#110 item 1 — already live-exposed)
  3. Unify the unlock redirect onto one builder

Authorization server: oidc-provider + storage adapter + consent; CIMD allowlist and resolver; Settings → MCP panel.

Resource server: the /api/mcp endpoint — transport, metadata, bearer challenge, Host/Origin validation, per-tool scopes.

Tools: get_nexus_info + attention roll-up; session lifecycle; workspace lifecycle; send_message.

Slice 2: the machine principal, unlocking create_workspace and start_workspace — the only two tools needing a vault key.

Findings that reversed a decision

Recorded in full in the spec. Three are worth repeating because they overturned choices already made:

  • Forgejo OAuth2 tokens are unscoped and account-wide, which killed delegating authorization to it — a token to list workspaces would also delete every repo on the forge.
  • MCP 2026-07-28 deprecated DCR in favour of CIMD, inverting which registration mechanism to build on.
  • @modelcontextprotocol/server v2.0.0 is Fetch-native, which reversed the decision to hand-roll the protocol layer and keeps /api/mcp inside the auth gate.
No due date
47% Completed
The MCP resource server, and the signing key out of the database
All checks were successful
ci / nexus (pull_request) Successful in 9m34s
ci / images (pull_request) Successful in 10m8s
#170 opened 2026-09-17 05:06:47 +02:00 by lz
#161 opened 2026-09-15 21:17:25 +02:00 by lz
#158 opened 2026-09-15 18:25:32 +02:00 by lz
#157 opened 2026-09-15 18:25:13 +02:00 by lz
#156 opened 2026-09-15 18:25:01 +02:00 by lz
#155 opened 2026-09-15 18:24:45 +02:00 by lz
#153 opened 2026-09-15 18:24:05 +02:00 by lz
#140 opened 2026-09-11 11:06:03 +02:00 by lz