Files
Gitea-Tools/docs/mcp-daemon-import-guard.md
T
sysadmin a1e5c33bfc feat(guard): native MCP transport binding and contaminated-review quarantine (Closes #695)
Bind mutation/credential paths to a process-local native MCP runtime so env
spoofing, direct imports, and offline helpers cannot reconstruct session gates
after native transport failure. Quarantine contaminated formal reviews under
controller authority and honor quarantine in review feedback, merge eligibility,
merge mutation, and canonical handoff validation. Add regression coverage for
the second (PR #694 / review 427) incident class.
2026-07-13 05:57:42 -04:00

3.0 KiB

MCP daemon import and native-transport guard (#558 / #695)

Problem

During deadlock debugging and the PR #694 incident (#695), agents imported gitea_mcp_server or ran credential helpers from a raw shell / offline helper, bypassing native MCP transport, preflight purity, and role gates. Contaminated formal reviews then looked identical to native approvals.

Rule

Mutation auth, keychain fill, and controller quarantine require a native MCP transport runtime established only by the official entrypoint.

Context Allowed
Official MCP entrypoint (mcp_server.py / gitea_mcp_server __main__) calls mark_sanctioned_daemon() and holds a process-local runtime token yes
pytest (hermetic unit tests) yes
GITEA_MCP_SANCTIONED_DAEMON=1 alone (no process-local native runtime) no (#695)
GITEA_ALLOW_DIRECT_MCP_IMPORT=1 in LLM sessions no — never set in agent sessions
GITEA_ALLOW_KEYCHAIN_CLI=1 in LLM sessions no — human operator only
bare python -c 'import gitea_mcp_server; …' or offline runners no
keychain fill outside native/pytest no

Native runtime is process-local: a random token bound to the daemon PID. It is never reconstructed from environment variables, session-state files, or importing internals in a fresh Python process.

Contaminated review quarantine (#695 AC8)

Controller/reconciler/merger profiles may call gitea_quarantine_contaminated_review with explicit confirmation:

QUARANTINE CONTAMINATED REVIEW <review_id> PR <pr_number>

Quarantine records are durable under the MCP session-state root and are honored by:

  • gitea_get_pr_review_feedback (quarantined approvals do not authorize merge)
  • gitea_check_pr_eligibility action=merge
  • gitea_merge_pr (mutation)
  • merger lease adoption paths that read approval_at_current_head

Forensic Gitea reviews and historical comments are never deleted.

STOP after native MCP failure (AC10)

If the native MCP namespace dies (EOF, capability disconnect, session death):

  1. STOP. State BLOCKED + DIAGNOSE.
  2. Do not import gitea_mcp_server from a standalone process.
  3. Do not run offline_mcp_helper.py, offline_mcp_runner.py, run_quarantine.py, or any offline mutation helper.
  4. Do not set direct-import, keychain-bypass, or raw-token environment variables.
  5. Reconnect / restart the official MCP daemon; resume only via native tools.

Any further native MCP failure is a hard stop. Do not construct another fallback.

Canonical approval claims (AC7)

Comments that claim approved / ready-to-merge / WHO_IS_NEXT: merger / MERGE_READY: true must include:

NATIVE_REVIEW_PROOF: transport=native_mcp; …

Claims that cite offline/import helpers are rejected even if a proof line is present.

Operator note

LLM sessions must never set allow-direct-import, allow-keychain-cli, or raw token overrides. Those are human-only escape hatches outside agent workflows.