Add docs/architecture/adr-0001-mcp-control-plane-boundaries.md. Confirms the already-documented Control Plane direction and extends it to Jenkins and GlitchTip: package/server boundaries (common, gitea-mcp, jenkins-mcp, glitchtip-mcp/observability-mcp/ops-mcp, release-mcp), recommended GlitchTip placement with alternatives, reaffirmed rules (one server per boundary, service-local creds, read-only first, namespaced allowed_operations, audited mutations, orchestrators are not credential sinks), hard phase-1 non-goals, consequences, and explicit open owner decisions. Does not reopen the settled direction. Documentation only; no code behavior changed. No Jenkins/GlitchTip implementation. Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
8.2 KiB
ADR-0001: Confirm and extend the MCP Control Plane trust-boundary model for Jenkins and GlitchTip
- Status: Proposed
- Date: 2026-07-02
- Issue: #71
- Supersedes / relates to: confirms and extends
docs/tool-boundaries.md,docs/safety-model.md,docs/credential-isolation.md,docs/release-workflows.md,docs/gitea-execution-profiles.md. Umbrella tracking: #75. Applied to docs by: #79.
1. Context
The MCP Control Plane direction is already decided in the existing architecture docs. This ADR does not reopen that decision. It exists to:
- Confirm the established model in one authoritative place, and
- Extend it to the two concrete services now under consideration — Jenkins (CI/CD visibility) and GlitchTip (error/observability).
What the existing docs already establish (and this ADR reaffirms):
- The project is named MCP Control Plane and is intended to group the
packages
common,gitea-mcp,jenkins-mcp,ops-mcp, andrelease-mcp(tool-boundaries.md). - One MCP server per trust boundary; there is no single "everything" server
(
tool-boundaries.md). - Separate credentials per service, each server instantiated with its own
dedicated
.env; strict isolation — e.g.gitea-mcphas no Jenkins or Ops tokens (credential-isolation.md). - All mutating actions are audited and require confirmation; production
actions need a hard gate; secrets are redacted from logs, tool output, and
storage (
safety-model.md). - The execution-profile model —
allowed_operations/forbidden_operations(forbidden wins), deny-by-default, fail-closed, verified identity viagitea_whoami, self-review/self-merge prevention, token-by-reference only (gitea-execution-profiles.md). That doc already names GlitchTip as a boundarygitea-mcpmust not absorb. - A future
release-mcporchestrator may coordinate across packages but must be "coordination, not consolidation" — it must not hold every service's credentials (release-workflows.md).
gitea-execution-profiles.md is explicit: gitea-mcp "must not add or
absorb Jenkins, Ops, GlitchTip, Release, deploy, rollback, migration, restart,
or production behavior." This ADR builds directly on that rule.
2. Decision
2.1 Repository shape
This repository (Gitea-Tools) is, in practice, the gitea-mcp package of
the Control Plane. Jenkins and GlitchTip work must not be added to it.
Recommended direction: extract the Control Plane into a dedicated
mcp-control-plane monorepo (as the existing docs already name) with one
package per boundary, and treat this repo either as the seed of that monorepo's
gitea-mcp package or as a package that is moved into it. The final choice
(monorepo now vs. later; move vs. seed) is an open owner decision (§5).
Until that is settled, the operative rule stands: no Jenkins/GlitchTip code
lands in this repo.
2.2 Package / server boundaries
| Package | Trust boundary | Phase-1 posture |
|---|---|---|
common |
Shared, credential-free library (profile schema, audit/redaction helpers, API/pagination/failure client, allowed_operations model). Holds no credentials. |
Extract shared pieces only as approved (§5) |
gitea-mcp |
Source-control & work items (issues, PRs, comments). Gitea creds only. | Exists (this repo) |
jenkins-mcp |
CI/CD visibility. Jenkins creds only. | Read-only build status/visibility |
GlitchTip boundary — glitchtip-mcp (recommended), or observability-mcp, or fold into ops-mcp |
Error/event observability. GlitchTip creds only. | Read-only error/event listing |
ops-mcp |
Live host/health/status/log checks. Ops creds only. | Read-only (per existing docs) |
release-mcp / orchestrator |
Coordinates across boundaries; composes other servers' tools. Not a credential sink. | Design-only in phase 1 |
Recommended GlitchTip placement: a dedicated glitchtip-mcp server.
Rationale — GlitchTip has its own API surface and its own credential, and error
tracking is a distinct trust boundary from live host checks; a dedicated server
is the cleanest fit for "one server per trust boundary."
- Alternative A —
observability-mcp: a broader observability boundary that could later also cover metrics/log/error sources beyond GlitchTip. Choose this if you expect several observability backends and want one boundary for them. - Alternative B — fold into
ops-mcp: minimizes package count, but mixes app-error observability with host/health checks; acceptable only if kept strictly read-only and the credentials are still GlitchTip-specific. Least recommended because it blurs two boundaries.
The final name/placement is an open owner decision (§5). Downstream issues (#73 GlitchTip read tools, #79 doc updates, #80 labels) must use whatever name is chosen here.
2.3 Rules (reaffirmed, now spanning all boundaries)
- One MCP server per trust boundary. No single "everything" MCP server.
- Separate credentials per service; tokens remain service-local. Each server
has its own
.env; e.g. a GlitchTip server never holds Gitea write tokens. - Read-only first. New service surfaces (Jenkins, GlitchTip) begin read-only.
- Mutations require explicit
allowed_operations, namespaced per service (e.g.gitea.issue.create,jenkins.build.read,glitchtip.event.read);forbidden_operationsalways overrides; deny-by-default; fail-closed. - Mutating actions require audit logging with verified identity and outcome,
and secret redaction (per
safety-model.md). - Orchestrators coordinate; they must not become credential sinks. Cross-service workflows compose per-service tools; no orchestrator centralizes all tokens.
3. Phase-1 non-goals (hard)
- No Jenkins build triggers.
- No deploy triggers.
- No parameterized job launches.
- No automatic GlitchTip-to-Gitea issue filing.
- No GlitchTip MCP server holding Gitea write credentials.
- No Jenkins or GlitchTip code inside
mcp_server.py(thegitea-mcpentrypoint).
4. Consequences
- Jenkins/GlitchTip work proceeds as design/read-only first, in their own packages/servers, gated behind this ADR's decisions.
- The
gitea-mcpmonolith (mcp_server.py) does not grow to host other services; that pressure is redirected to separate packages and thecommonextraction (relates to the #65 refactor, which remains independent). - Cross-service "file a Gitea issue from a GlitchTip error" becomes an orchestrator/runbook concern (composing GlitchTip-read + Gitea-write tools), never a single dual-credential server (see #74/#78).
- Naming/label decisions (#80) and doc updates (#79) inherit the choices here.
5. Open owner decisions
These are intentionally not decided by this ADR and must be resolved by the repo owner before the corresponding implementation issues proceed:
- Monorepo vs. this repo. Does a separate
mcp-control-planerepo get created now (withgitea-mcpmoved into it), or does this repo become the monorepo, or does it stay Gitea-only for now while others live elsewhere? - GlitchTip placement.
glitchtip-mcp(recommended),observability-mcp, or folded intoops-mcp? - Cross-service filing mechanism. Should GlitchTip-to-Gitea filing be an
LLM runbook only, or a carefully constrained orchestrator workflow
(
release-mcp) with dry-run + explicit invocation + Gitea profile gating? commonpackage scope. Which shared pieces are approved for extraction intocommonnow — profile schema, audit/redaction, API client (pagination/failure handling),allowed_operationsmodel — versus deferred?
6. References
docs/tool-boundaries.mddocs/safety-model.mddocs/credential-isolation.mddocs/release-workflows.mddocs/gitea-execution-profiles.md- Tracking/umbrella: #75 · Doc application: #79 · Jenkins design: #72/#77 · GlitchTip design: #73 · Cross-service filing: #74/#78 · Labels: #80