Skip to content

feat(caddy): expose MCP gateway at /mcp/* (bearer-gated) for tailnet clients#63

Merged
AlienWalker1995 merged 1 commit into
mainfrom
feat/caddy-mcp-route
Jun 28, 2026
Merged

feat(caddy): expose MCP gateway at /mcp/* (bearer-gated) for tailnet clients#63
AlienWalker1995 merged 1 commit into
mainfrom
feat/caddy-mcp-route

Conversation

@AlienWalker1995

Copy link
Copy Markdown
Owner

Why

Remote MCP clients (Cline/Cursor on other tailnet PCs) couldn't reach the aggregated MCP gateway — it's 127.0.0.1-only, on a network Caddy couldn't reach, and has no auth of its own. The gateway already bundles all 8 servers (n8n, comfyui, orchestration, searxng, blog-mcp, playwright, qdrant-rag, codebase-memory), so one bearer-gated route exposes every tool through a single Cline entry.

What

  • secrets/.env.sops — add MCP_GATEWAY_TOKEN (env-form → runtime/.env).
  • docker-compose.ymlmcp-gateway joins proxy-net; MCP_GATEWAY_TOKEN passed into Caddy's env.
  • auth/caddy/Caddyfile/mcp /mcp/* bypass route: 401 unless Authorization: Bearer {$MCP_GATEWAY_TOKEN}; passed through unstripped (gateway serves /mcp) with flush_interval -1 for SSE/streamable-HTTP. Tailnet-only.

Client config (Cline)

"ordo": { "type": "streamableHttp", "url": "https://<tailnet-host>/mcp", "headers": { "Authorization": "Bearer <MCP_GATEWAY_TOKEN>" } }

Validation (live)

  • POST /mcp without token → 401.
  • with token → 200 MCP initialize from the Docker MCP Gateway (all 8 servers' tools).

No secret value committed (encrypted blob + env-var reference only).

🤖 Generated with Claude Code

… tailnet clients

Remote MCP clients (Cline/Cursor on other tailnet PCs) had no way to reach the
aggregated tool gateway: it's 127.0.0.1-only, on a network Caddy couldn't reach,
and has no auth of its own. One endpoint already aggregates all 8 servers
(n8n, comfyui, orchestration, searxng, blog-mcp, playwright, qdrant-rag,
codebase-memory), so a single bearer-gated route exposes everything.

- secrets/.env.sops: add MCP_GATEWAY_TOKEN (env-form, decrypts to runtime/.env).
- docker-compose.yml: add model... mcp-gateway to proxy-net so Caddy can reach it;
  pass MCP_GATEWAY_TOKEN into caddy's env.
- auth/caddy/Caddyfile: /mcp /mcp/* bypass route — 401 unless the request carries
  Authorization: Bearer {$MCP_GATEWAY_TOKEN}; passed through unstripped (gateway
  serves /mcp) with flush_interval -1 for SSE/streamable-HTTP. Tailnet-only.

Validated live: POST /mcp without the token -> 401; with it -> 200 MCP initialize
from the Docker MCP Gateway. No secret value is committed (only the encrypted blob
and an env-var reference).

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
@AlienWalker1995 AlienWalker1995 merged commit 186bbe6 into main Jun 28, 2026
4 checks passed
@AlienWalker1995 AlienWalker1995 deleted the feat/caddy-mcp-route branch June 28, 2026 14:52
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant