Files
dap-was-dapms/docs/decisions/ADR-0006-no-authentication-in-mcp.md
koseokmin cb29b192b4 docs를 저장소로 되돌리고 계약 예제를 복원한다
5cfb8a1이 .gitignore에 docs/를 넣고 68개 파일을 지웠다. 그런데
AgentBuilderContractExampleTest, ToolBundleContractExampleTest,
ArchitectureDocumentContractTest는 docs/ 아래 계약 예제와 architecture
문서를 입력으로 직접 읽는다. 그 결과 clean clone에서 테스트 10건이
입력을 찾지 못해 실패했다.

제외 범위를 원래 의도대로 좁힌다. 에이전트 산출물(AGENTS.md, .agents/,
.codex/, docs/superpowers/)은 계속 제외하고 저장소 문서는 추적한다.

문서는 삭제 직전 상태(3de052a)를 기준으로 복원하고, 그 위에 main 코드와
대조해 어긋난 부분을 고쳤다.

- ADR-0007을 Superseded로 바꾸고 ADR-0013을 새로 쓴다. route당 Tool
  Service N개가 최종안이며, PortalToolRegistryClient가 이미 route별로
  N개를 유지하고 있는데 ADR-0007은 "bundles는 항상 한 항목"을 Accepted
  상태로 주장하고 있었다. ADR-0009 결정 4도 부분 대체한다.
- ADR-0008 파일 헤더가 Accepted였으나 ADR-0009가 이미 대체한 상태였다.
- 6078852의 endpoint 소유권 반전이 반영되지 않은 서술을 계약 v0.2,
  bundle 설정 예제, Tool 적재 안내에서 고친다.
- Portal registry 계약 v0.1과 route key 규약을 새로 문서화한다. 둘 다
  구현은 있는데 계약 문서가 없었다.
- MCP SDK 2.0.0 SBOM을 추가한다.

번호 주석: ADR-0011과 0012는 feature/mcp-integration이 Tool inputSchema
정책에 쓰고 있어 비워 둔다.

Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
2026-08-22 23:27:56 +09:00

83 lines
5.2 KiB
Markdown

# ADR-0006 MCP Server는 인증·인가를 하지 않는다
- 상태: Accepted
- 결정일: 2026-08-01
- 관련 결정: [ADR-0001](ADR-0001-stateless-execution-boundary.md), [ADR-0010](ADR-0010-tool-service-manifest-owns-execution-endpoint.md), [ADR-0013](ADR-0013-portal-owns-route-and-endpoint-registry.md)
> 이 ADR은 **inbound** 신뢰 경계를 다룬다. outbound 목적지는
> [ADR-0010](ADR-0010-tool-service-manifest-owns-execution-endpoint.md) 이후 Tool Service 매니페스트가 정하며,
> 도메인 허용목록도 egress NetworkPolicy도 없다. 아래 "책임 소재" 표의 NetworkPolicy 항목은 ingress 통제이므로
> outbound 위험을 덮지 않는다.
## 배경
Tool 실행 권한은 Agent Builder가 Agent를 구성할 때 이미 확인하고 넘어온다.
MCP Server는 Agent Builder가 지정한 Tool을 검증·실행하는 계층이므로 권한을 다시 판단할 근거가 없다.
문제는 MCP가 **판단하지 않는 계층인 동시에 집행 지점**이라는 데 있다.
MCP는 이 배포에 속한 모든 Tool Service에 도달할 수 있는 유일한 경로다.
따라서 "MCP는 아무것도 하지 않는다"는 결정은, 그러면 **누가 하는가**를 함께 적지 않으면
세 계층이 서로 상대가 확인했다고 가정하는 공백을 만든다.
이 문서는 그 공백을 막기 위해 책임 소재를 명시한다.
## 결정
MCP Server는 인증(authentication)과 인가(authorization)를 수행하지 않는다.
- 요청자의 신원을 검증하지 않는다.
- Tool 실행 권한을 판단하지 않는다.
- `employee-no`·`virtual-employee-no`를 복호화·검증·저장하지 않는다.
- Authorization 헤더를 해석하지 않는다. `mcp.tool-client.forward-authorization`이 켜져 있으면
값을 그대로 전달만 한다.
이에 따라 무검증 JWT decode 구현(`JwtClaimExtractor`, `UnverifiedJwtClaimExtractor`)을 삭제한다.
검증하지 않는 인증 코드는 없는 것보다 나쁘다. 이후 누군가 그 claim을 판단 근거로 쓸 여지를 남기고,
코드베이스에 인증이 처리되고 있다는 잘못된 인상을 준다.
## 책임 소재
| 책임 | 주체 | 근거 |
|---|---|---|
| 호출자가 Agent Builder인지 보장 | **플랫폼(NetworkPolicy)** | Helm Chart의 `templates/networkpolicy.yaml`. 환경별 허용 namespace는 `values-{env}.yaml``global.agentBuilderNamespace` |
| 사용자 인증, Tool 실행 권한 판단 | **Agent Builder** | Agent 구성 시점에 확인 |
| 사원 식별자 복호화와 업무 권한 집행 | **Tool Service** | KMS에서 발급받은 키 사용 |
| 요청 형식·schema 검증, 단일 Tool 실행 | **MCP Server** | ADR-0001 |
## 이 결정이 성립하기 위한 전제
**전제 1 — 네트워크가 호출자를 고정한다.**
MCP는 요청자를 확인하지 않으므로, `/mcp`에 도달할 수 있다는 것 자체가 곧 인가다.
NetworkPolicy로 Agent Builder namespace만 8080에 접근하도록 제한한다.
**이 정책 없이 배포하면 클러스터 안의 어떤 Pod이든 Tool을 실행할 수 있다.**
정책은 선택적 강화가 아니라 이 ADR의 성립 조건이다.
그래서 Helm Chart에 비활성화 스위치를 두지 않았고, `HelmDeploymentContractTest`
조건부 렌더링이 들어오는 것까지 막는다. values 한 줄로 인가가 사라지지 않게 하기 위해서다.
**전제 2 — 사원 식별자의 신뢰는 Tool Service가 확보한다.**
`employee-no`·`virtual-employee-no`는 암호화되어 전달되고, 복호화 키는 사내 KMS에서 발급받는다.
MCP는 키를 갖지 않으므로 값을 읽을 수 없고, 따라서 위조 여부도 판별할 수 없다.
Tool 파트가 확인할 항목:
- 복호화는 KMS 키로만 가능하므로 **기밀성**은 확보된다.
**위조 방지**는 암호화 키의 배포 범위에 달려 있다. 암호화 키를 널리 배포하면
임의의 사원번호를 스스로 암호화해 넣을 수 있으므로, 키 배포 범위를 신뢰 경계와 맞춘다.
- 동일한 암호문의 재사용(replay)을 허용할지, 만료·nonce를 둘지 결정한다.
- 두 헤더가 모두 없는 요청의 처리 방침을 정한다. 현재 계약에서 두 값은 선택값이다.
**전제 3 — 감사 추적은 세 계층의 로그를 합쳐야 완성된다.**
MCP 로그에는 `guid``x-request-id`만 남는다.
사원 식별자는 개인 식별자이므로 암호문이라도 기록하지 않는다.
따라서 "누가 조회했는가"는 MCP 로그만으로 답할 수 없다.
`guid`를 Agent Builder·MCP·Tool Service가 공통 상관 키로 사용해 세 로그를 연결한다.
규제 감사 요건이 확정되면 별도 durable sink를 설계한다.
## 영향
- MCP에 인증 코드를 추가하지 않는다. 필요가 생기면 이 ADR을 대체하는 새 ADR을 먼저 쓴다.
- NetworkPolicy는 배포 필수 구성요소다. 누락은 설정 실수가 아니라 보안 결함으로 다룬다.
- 인증 모델이 token 기반으로 바뀌면 이 결정과 전제 1을 함께 재검토한다.
- `forward-authorization` 설정은 유지한다. 검증이 아니라 통과 전달이며,
Tool Service가 자체 인증을 도입할 때 필요한 연결점이다.