agent에게 API 스펙만 주는 법
에이전트가 HTTP 클라이언트를 붙일 때 가장 흔한 실패는 스펙에 없는 path·메서드·필드를 지어내는 것입니다. 채팅에 “대략 이런 API야”라고 풀어 쓰기보다, OpenAPI(Swagger) 문서 한 장을 읽고 그 안의 paths·components만 쓰게 하는 편이 계약이 분명합니다.
이 글은 **스펙 파일은 어디에 두나? · 예시 응답은 어떻게 주나? · 환각을 줄이려면?**만 다룹니다. mcp-tool-schema는 MCP 도구 JSON Schema 문장 설계이고, mcp-resource-vs-tool은 resource/tool 선택입니다. 여기서는 에이전트 컨텍스트에 OpenAPI만 공급하는 축입니다. 요금·플랜·토큰·제휴 링크는 없습니다.
근거는 OpenAPI Specification v3.1.0(Paths·Media Type·Response·Example Object)과 에이전트에 읽기 전용 스펙 파일을 넣는 흔한 워크플로입니다.
스펙 파일은 어디에 두나?
한 줄 답: 저장소에 단일 진실(OpenAPI YAML/JSON) 을 두고, 에이전트에게는 그 경로·URI만 가리키십시오. 프롬프트에 스펙 본문을 매번 붙여 넣지 않습니다.
실무 배치:
| 위치 | 역할 | 에이전트에 주는 방식 |
|---|---|---|
openapi.yaml / openapi.json (루트·docs/·specs/) | 계약의 단일 소스 | 상대 경로를 Rule/AGENTS.md에 고정 |
| CI에서 생성한 스냅샷 | 코드에서 뽑은 최신 스키마 | 커밋된 산출물 경로만 참조 |
| MCP resource URI | 호스트가 컨텍스트로 끌어오는 읽기 전용 | resources/read로 스펙만 공급 |
| 내부 문서 사이트 HTML | 사람용 설명 | 에이전트 입력으로는 OpenAPI 원문을 우선 |
권장 프롬프트 한 줄:
API contract: only <repo>/docs/openapi.yaml
Allowed: paths + components declared there.
Forbidden: invent endpoints, fields, status codes, or auth schemes.
피해야 할 배치:
- 채팅에 path 목록만 메모처럼 붙여 넣고 스키마는 생략하기 → 필드·타입이 바로 환각됩니다.
- “README의 curl 예시만” 주고 OpenAPI는 숨기기 → 예시와 실제 계약이 어긋날 때 에이전트가 예시를 진실로 취급합니다.
- 여러 버전의
openapi-v1.yaml/openapi-v2.yaml을 동시에 컨텍스트에 넣기 → 어느 버전이 허용인지 Rule에 하나만 적으십시오.
스펙이 크면 전체를 매 턴에 넣지 말고, 작업에 필요한 path prefix만 잘라 읽게 하거나 $ref가 해석된 부분 스펙을 생성해 두십시오. 잘라 낼 때도 원본 파일 경로는 남깁니다.
예시 응답은 어떻게 주나?
한 줄 답: 예시는 OpenAPI Media Type Object의 example 또는 examples에 넣고, 스키마(schema)와 함께 줍니다. 채팅에 JSON만 던지지 않습니다.
OpenAPI 3.1에서 요청·응답 본문 예시는 Media Type Object에 둡니다. example과 examples는 상호 배타이며, Media Type 쪽 값이 스키마에 있는 example을 덮어씁니다. Response Object의 content는 미디어 타입 키 → Media Type Object 맵입니다.
최소 형태(개념):
responses:
"200":
description: OK
content:
application/json:
schema:
$ref: "#/components/schemas/Item"
examples:
sample:
summary: typical item
value:
id: "item_1"
name: "widget"
"404":
description: Not found
content:
application/json:
schema:
$ref: "#/components/schemas/Error"
example:
code: "not_found"
message: "Item not found"
에이전트에 줄 때 규칙:
- 성공·실패를 같이 —
200만 있으면 에러 본문을 지어냅니다.4xx/5xx스키마·예시를 스펙에 두십시오. - 필드 이름은 스키마와 동일 — 예시에만 있는 키는 “문서화되지 않은 필드”로 오해됩니다.
- 여러 변형은
examples맵 —empty_list,with_cursor처럼 이름을 붙여 어떤 경우를 보여 주는지 밝히십시오. - 외부 샘플 파일 — Example Object의
externalValue로 URL을 가리킬 수 있으나, 에이전트가 네트워크를 못 쓰면 인라인value가 안전합니다. - 요청 본문도 동일 — Request Body의 Media Type에도
example/examples를 두면 호출 payload 환각이 줄어듭니다.
채팅용 보조 문장은 짧게:
Prefer response examples from the OpenAPI Media Type Object.
Do not treat README curl snippets as the contract if they diverge.
환각을 줄이려면?
한 줄 답: “스펙에 없으면 호출·작성하지 말 것”을 금지 규칙으로 고정하고, 호출 전 path·method·required를 스펙과 대조하게 하십시오.
체크리스트:
[ ] Single OpenAPI path in Rule / brief (one file, one version)
[ ] Agent may only use operationId or method+path listed under paths
[ ] required parameters / requestBody fields must come from the spec
[ ] Status codes and error bodies must match declared responses
[ ] If unsure: stop and ask / open a ticket — do not invent
[ ] After edit: regenerate or validate OpenAPI (spectral, openapi-cli, etc.)
환각이 나는 전형 패턴과 대응:
| 증상 | 원인 | 대응 |
|---|---|---|
/v2/widgets처럼 없는 path | 자연어 설명만 줌 | paths 키만 허용 |
camelCase/snake_case 혼용 | 예시와 스키마 불일치 | 예시=schema 정렬 |
| 임의 헤더·쿼리 | Parameter Object 미제공 | parameters·required 명시 |
| 200 본문만 가정 | 에러 응답 부재 | 4xx/default 정의 |
| 옛 엔드포인트 재등장 | 컨텍스트에 구버전 혼입 | 버전·파일 하나 |
도구가 있다면 스펙을 파싱해 허용 목록을 만든 뒤 HTTP를 치게 하는 편이 채팅 주의보다 강합니다. 도구가 없어도 Done 정의에 “호출한 path가 openapi paths에 존재함”을 넣으면 사람 리뷰가 쉬워집니다.
인접 글: MCP로 스펙을 resource로 붙일지는 mcp-resource-vs-tool, 도구 인자 문장은 mcp-tool-schema입니다.
한 줄 정리: 단일 OpenAPI 파일 경로 → Media Type 예시로 성공/실패 고정 → paths 밖 호출 금지. 자연어 API 설명만으로 에이전트를 보내지 마십시오.
FAQ
OpenAPI 2.0(Swagger)도 같은가?
계약 파일을 주고 paths 밖을 금하는 원리는 같습니다. 예시 필드 위치·문법은 3.x Media Type Object 기준을 이 글에서 썼습니다. 팀이 2.0이면 그 문서의 examples/definitions 규칙에 맞추십시오.
스펙이 아직 없는데 에이전트를 써도 되나?
먼저 최소 OpenAPI(path·method·schema·한두 예시)를 커밋한 뒤 에이전트를 붙이는 편이 안전합니다. 스펙 없이 코드만 생성하면 나중에 계약을 맞추는 비용이 큽니다.
README와 OpenAPI가 다르면?
에이전트 규칙상 OpenAPI가 우선입니다. README는 사람을 위한 서술로 두고, 어긋나면 스펙을 고치거나 README를 고치십시오—에이전트에게 “적당히 합쳐라”고 하지 마십시오.
스펙 전체를 컨텍스트에 넣으면 너무 큰데?
path prefix·태그·operationId 목록으로 작업 범위를 좁히고, 해당 Path Item·관련 $ref만 읽게 하십시오. 그래도 금지: 목록에 없는 path 발명은 유지합니다.
출처 (Sources)
- OpenAPI Specification v3.1.0 — Paths, Media Type (
example/examples), Response, Example Object - OpenAPI Initiative · OAS — 명세 허브
- 인접: mcp-resource-vs-tool(스펙을 resource로 둘지), mcp-tool-schema(도구 스키마 문장)