블로그 AI / Agent

AI Coding Agent는 어떻게 동작하는가? Claude Code, Codex, Xcode 27 Agent, Tool Calling과 JSON 데이터 해설

Claude Code, Codex, Xcode 27을 열면 화면은 채팅처럼 보인다. 저장소를 고치고, 테스트를 돌리고, 시뮬레이터를 탭하는 것은 그 자연어 답이 아니다.

AI Coding Agent의 일하는 방식은 이렇다. 모델이 다음 단계를 추론하고 Tool Calling을 낸다. 로컬 또는 IDE의 harness가 도구를 실행하고, 구조화 결과를 다시 넣는다. 파라미터와 결과는 거의 항상 JSON이다.

이 글에서는:

이것만 기억하세요: 화면은 채팅처럼 보이지만, 실제로 일하는 것은 Tool Calling이다. 모델이 도구를 고르고 JSON 파라미터를 채운다. 파일을 고치고, 테스트를 돌리고, 시뮬레이터에 닿을 수 있는지는 harness가 준 도구, 권한, 검증에 달렸다. 아래는 루프 → 도구 호출 → 세 제품 → JSON 계약으로 가른다.

채팅 창이 아니라 루프다

완성이 푸는 문제는 「다음 줄을 무엇으로 쓸까」다. Coding Agent가 푸는 문제는 「이 목표를 실제 프로젝트에서 어떻게 끝낼까」다: 컨텍스트를 읽고, 도구를 고르고, 코드를 고치고, 명령을 돌리고, 결과를 보고, 다시 결정한다.

공식 문서의 말은 바뀌어도 형태는 같다. Claude Code는 컨텍스트 수집 → 행동 → 결과 검증으로 쓰고, Xcode 27은 먼저 계획하고, 파일을 고치고, 빌드 / 테스트 / Preview / 시뮬레이터로 스스로 검증한다. 바닥은 둘 다:

  1. 1
    관찰

    파일을 읽고, 심볼을 찾고, git 상태를 보고, 실패한 테스트 로그를 가져온다. 이 단계가 없으면 다음 패치는 추측이다.

  2. 2
    결정

    모델은 컨텍스트에서 다음을 고른다: 다시 읽고, 다시 찾고, 한 곳을 고치고, 명령 하나를 돌리거나, 한 줄 묻는다.

  3. 3
    실행

    harness가 tool call을 받아 권한과 샌드박스 안에서 실제로 돌린다. 이때 모델은 디스크를 건드리지 않는다.

  4. 4
    되돌려 쓰기

    도구 결과는 텍스트 또는 JSON이 되어 컨텍스트로 돌아간다. 모델은 새 증거를 보고 이어 가거나, 끝났다고 선언한다.

당신도 이 루프 안에 있다: 끊고, 방향을 바꾸고, 고위험 동작을 승인한다. 모델은 추론을 맡고, harness는 도구, 권한, 세션, 「끝」의 정의를 맡는다. 네 제품이 제어권을 어떻게 겨루는지는 다음을 보라.

AI Coding Agent는 더 이상 코드 완성이 아니다: Codex, Claude Code, OpenCode, DeepSeek Harness는 무엇을 겨루는가?

이 글은 「루프가 어떻게 도는지, JSON이 어느 홉에 나오는지」만 가른다. 기술 스택 층은

2026 AI Agent 스택: LLM, MCP, Function Calling, JSON Schema를 어떻게 조합할까?를 참고.

Tool Calling: 파라미터가 곧 JSON

Tool Calling(Function Calling이라고도 한다)은 「모델이 코드를 쓸 줄 안다」의 다른 이름이 아니다. 구조화된 함수 호출이다. 모델이 당신이 선언한 도구 목록에서 이름을 고르고, 파라미터 계약에 맞는 JSON을 만든다.

OpenAI 호환 인터페이스에서 도구 정의의 parameters 필드 자체가 JSON Schema다:

도구 정의(parameters = JSON Schema)
{
  "type": "function",
  "function": {
    "name": "run_tests",
    "description": "Run the project test suite and return a structured summary.",
    "parameters": {
      "type": "object",
      "properties": {
        "suite": { "type": "string", "enum": ["unit", "integration", "e2e"] },
        "path": { "type": "string", "minLength": 1 }
      },
      "required": ["suite"],
      "additionalProperties": false
    }
  }
}

모델이 반환할 때 arguments는 이미 parse된 객체가 아니라, 문자열인 경우가 많다:

모델이 돌려준 tool_call(arguments는 문자열)
{
  "id": "call_8f21",
  "type": "function",
  "function": {
    "name": "run_tests",
    "arguments": "{\"suite\":\"unit\",\"path\":\"src/auth\"}"
  }
}

그래서 업무 층은 적어도 두 가지를 한다. 먼저 문자열을 유효한 JSON으로 파싱하고, 선언한 schema로 필드, 타입, enum을 검증한다. 따옴표 누락, 쉼표 추가, 선언하지 않은 키는 모두 이 홉에서 일어난다. 「모델이 똑똑해 보인다」는 층이 아니다.

한 바퀴는 이렇다. 요청에 schema를 실어 보낸다 → 모델이 도구를 고르고 arguments를 만든다 → 당신이 파싱하고 검증한다 → 도구를 실행한다 → 결과를 tool message로 다시 넣는다 → 모델이 이어 간다. schema가 분명하면 첫 arguments가 맞고, 흐리면 루프가 공회전한다.

계약을 어떻게 쓸지, JSON Mode와 Strict Schema가 어디서 다른지는

AI Agent에 JSON Schema가 필요한 이유: Tool Calling부터 Structured Output까지를 보라.

Claude Code: 내장 도구 + 확장 층

Claude Code 공식 문서는 Agent를 두 조각으로 가른다: 추론하는 모델, 행동하는 도구. 도구가 없으면 Claude는 글만 돌린다. 도구가 있으면 저장소를 읽고, 파일을 고치고, 명령을 돌리고, 웹을 검색한다.

내장 도구는 대략 다섯 갈래다. 파일 조작(Read / Edit / Write), 검색(Grep / Glob), 실행(Bash), Web(WebSearch / WebFetch), 플러그인이 필요한 코드 인텔리전스(정의로 이동, 타입 오류). 하위 Agent, 당신에게 묻기도 도구다. 오케스트레이션용이다.

「실패한 테스트를 고친다」한 바퀴는 루프에서 이렇게 보일 수 있다:

  1. 1
    Bash가 테스트를 돌린다

    어떤 단언이 터졌는지 먼저 보고, 코드를 바로 건드리지 않는다.

  2. 2
    Grep / Read로 소스를 찾는다

    스택과 심볼로 알맞은 컨텍스트를 창에 넣는다.

  3. 3
    Edit가 정확하게 치환한다

    공식은 먼저 읽고 고친다: old_string → new_string. 읽지 않고 쓰지 않는다.

  4. 4
    테스트를 다시 돌린다

    결과가 컨텍스트로 돌아온다. 실패하면 다시 루프를 돌리지, 「됐을 것」이라고 말로만 하지 않는다.

확장 층은 이 루프 위에 얹힌다. 루프를 대체하지 않는다:

Claude Code의 엔지니어링 타협은 분명하다: 확률적 Agent + 결정적 Hooks. 세션 자체도 JSONL로 떨어져 복구와 분기가 쉽다. 디버깅하는 것은 「한 줄 채팅」이 아니라 tool 이벤트 줄인 경우가 많다.

Codex: 샌드박스, 승인, JSONL

Codex 역시 Agent loop를 돈다. 다만 제품의 중심은 「모델이 만든 명령이 어떻게 착지하는가」다.

Codex CLI를 터미널에서 실행할 때는, 먼저 샌드박스와 승인을 고른 뒤 모델이 움직이게 한다.

스위치 흔한 값 무엇을 제한하는가
sandbox read-only / workspace-write / danger-full-access 명령이 어디에 쓸 수 있는지, 네트워크에 나갈 수 있는지
approval-policy untrusted / on-request / never 권한 상승이나 고위험 동작에 사람이 눌러야 하는지

자동화에서는 codex exec --json를 쓴다. 표준 출력은 JSONL이 된다: thread / turn 시작과 끝, 명령 실행, 파일 변경, MCP 호출, 계획 갱신. CI 스크립트가 소비하는 것은 이벤트 스트림이지, 산문이 아니다.

codex exec --json 이벤트(예시)
{"type":"item.completed","item":{"id":"item_12","type":"command_execution","command":"npm test -- src/auth","exit_code":1,"aggregated_output":"FAIL src/auth/session.test.ts"}}
{"type":"item.completed","item":{"id":"item_13","type":"file_change","path":"src/auth/session.ts","kind":"update"}}
{"type":"turn.completed","usage":{"input_tokens":18420,"output_tokens":966}}

뒤에 붙는 시스템이 안정된 필드를 필요로 하면 --output-schema로 최종 답을 JSON Schema에 맞춘다. Tool Calling의 parameters와 같은 종류의 계약이다. 다만 제약을 거는 것은 「작업이 끝날 때의 그 JSON」이지, 중간 명령 하나하나가 아니다.

기본 codex exec는 읽기 전용 샌드박스다. 파일을 고치려면 --sandbox workspace-write를 명시한다. 디렉터리가 더 필요하면 --add-dir를 먼저 쓰고, 처음부터 danger-full-access로 가지 말 것.

Xcode 27 Agent: 계획, 검증, 에디터 도구

Apple은 WWDC 2026에서 Xcode 27을 「Apple 플랫폼에서 Agent와 함께 코드를 쓰는 곳」으로 두었다. 터미널 Agent와 달리, 도구 상자는 IDE 안에 있다.

Apple 보도자료

Xcode, agents, and you,

What’s new in Xcode 27가 몇 가지를 분명히 한다:

WWDC 랩은 Chat과 Agent를 문구 차이가 아니라 능력 차이로 말한다. Chat은 작은 고정 도구 집합만 가진다. Agent 모드는 명령줄과 Xcode 내부 도구(빌드, 테스트, Preview, 시뮬레이터)를 더한다. 기본 안전 모드는 권한 프롬프트다. Agent는 작업에 필요한 것에 닿을 수 있지만, 디스크를 마음대로 돌아다니지 못한다.

JSON 개발자에게 Xcode의 이 홉이 중요한 이유는, 검증 결과도 구조화되어 되돌아오기 때문이다. 빌드 실패, 테스트 요약, Preview 산출물이 Agent의 다음 입력이 된다. 백엔드에서 보는 것은 여전히 자기 API의 JSON인 경우가 많다. IDE 안에서 같은 루프가 소비하는 것은 Xcode 도구의 출력이다.

시스템 층 Siri AI는 App Intents를 쓰고, 이 에디터 Agent가 아니다. 둘을 「Apple에는 Agent가 하나뿐」으로 접지 말 것.

Siri AI는 AI Agent가 될까?를 보라.

세 곳 대조: 같은 루프, 다른 도구 상자

기능 목록은 점점 닮아 간다. 차이는 기본 도구, 실행 경계, 그리고 결과가 다음 턴 컨텍스트가 되는 방식이다.

Claude Code Codex Xcode 27 Agent
루프 관찰 → 행동 → 검증 같은 loop + 이벤트 스트림 계획 → 코드 수정 → IDE 검증
기본 도구 Read / Edit / Bash / Grep shell + MCP + plan 빌드 / 테스트 / Preview / 시뮬레이터
확장 Skills, MCP, Hooks MCP, Agents SDK, output-schema MCP 플러그인, ACP 외부 Agent
경계 권한 모드 + Hooks sandbox + approval-policy 프로젝트 권한 프롬프트 + 작업 디렉터리
기계가 읽을 수 있는 출구 세션 JSONL, tool 결과 exec --json, --output-schema diff, 산출물, 빌드/테스트 출력

고르기는 짧게 둬도 된다. 일반 다언어 저장소와 재사용 Skills면 Claude Code. 실제 머신에서 돌리면서 권한을 CI에 쓰려면 Codex. 목표가 Apple 플랫폼이고 검증이 Xcode 툴체인을 지나야 하면 Xcode 27. Xcode의 ACP는 후자가 앞의 둘을 배척하지 않게 한다. 외부 Agent는 에디터에 들어올 수 있지만, 빌드와 Preview는 여전히 Xcode의 도구다.

JSON 데이터는 어느 층에 있고, 누가 검증하는가

세 제품의 UI는 다르다. JSON이 나오는 위치는 안정적이다:

위치 전형 필드 누가 강하게 검증하는가
도구 선언 parameters / inputSchema 당신의 schema + SDK
모델 인수 tool_calls.arguments 먼저 parse, 그다음 schema
도구 회신 structuredContent / 로그 JSON outputSchema 또는 직접 검증
최종 답 response_format / output-schema Strict Schema + 업무 층

핵심 한 줄: API 층 schema는 모델 생성을 이끌고, 업무 층 schema는 더러운 데이터를 거절한다. 서로 대체하지 못한다. AI 출력에 왜 먼저 schema가 필요한지는

AI에 JSON Schema가 필요한 이유?를 보라.

Coding Agent용 도구 schema라면, 「언제 호출하고 언제 호출하지 말 것」을 쓰고, 선택지는 description에 묻지 말고 enum에 넣는다:

Coding Agent 도구 schema(붙여 검증)
{
  "$schema": "https://json-schema.org/draft/2020-12/schema",
  "type": "object",
  "required": ["action", "path"],
  "properties": {
    "action": { "type": "string", "enum": ["read", "edit", "test"] },
    "path": { "type": "string", "minLength": 1 },
    "suite": { "type": "string", "enum": ["unit", "integration"] },
    "old_string": { "type": "string" },
    "new_string": { "type": "string" }
  },
  "additionalProperties": false,
  "allOf": [
    {
      "if": { "properties": { "action": { "const": "edit" } } },
      "then": { "required": ["old_string", "new_string"] }
    },
    {
      "if": { "properties": { "action": { "const": "test" } } },
      "then": { "required": ["suite"] }
    }
  ]
}

모델이 {"action":"edit","path":"src/a.ts"}를 내고 old_string이 없으면, schema가 실행 층에서 막는다. 사후에 diff를 보는 것보다 싸다.

JSONNote로 tool 파라미터 디버깅

Agent 개발에서 가장 느린 것은 대개 프롬프트가 아니다. 실패한 tool call 한 번이다. JSONNote는 브라우저 로컬에서 돈다. 키와 저장소 내용은 올리지 않는다.

  1. 1
    arguments가 parse되는지 먼저 본다

    모델이 돌려준 문자열을 JSON 포맷에 넣는다. 따옴표 누락, 끝 쉼표, 채팅 앱이 자른 hash가 여기서 드러난다.

  2. 2
    그다음 schema로 검증한다

    도구 정의와 실제 arguments를 JSON Schema에 같이 넣는다. enum이 틀리고, required가 빠지고, extra 필드가 늘어난 것이 모델의 「미안하다」보다 쓸모 있다.

  3. 3
    두 호출을 비교한다

    description을 고치거나 additionalProperties: false를 넣은 뒤, JSON Diff로 파라미터 회귀를 본다.

  4. 4
    디버그 현장을 공유한다

    URL Hash 공유로 tool JSON을 링크에 넣는다. 동료가 열면 재현되고, 데이터는 서버를 거치지 않는다.

자주 묻는 질문

AI Coding Agent와 코드 완성은 본질적으로 무엇이 다른가?

완성은 다음 한 줄만 제안한다. Coding Agent는 저장소를 읽고, 파일을 고치고, 명령을 돌리고, 외부 도구를 부르며, 루프 안에서 도구 결과를 보고 계속 결정한다. 차이는 문장이 아니라, 행동할 수 있는가이다.

모델이 내 디스크 파일을 직접 고치는가?

아니다. 모델은 tool call만 낸다. 대개 JSON 한 덩어리다. 파일을 쓰고, shell을 돌리고, 시뮬레이터를 탭하는 것은 로컬 harness다. 도구가 없거나, 권한이 거절되거나, 파라미터 검증이 실패하면 디스크에서는 아무 일도 없다.

Claude Code, Codex, Xcode 27 Agent 중 무엇이 더 나은가?

통일된 우승자는 없다. 일반 저장소와 Skills / MCP면 Claude Code. 샌드박스, 승인, CI의 JSONL 이벤트면 Codex. Apple 플랫폼에서 빌드 / Preview / 시뮬레이터 검증이 필요하면 Xcode 27 Agent. Xcode는 ACP로 외부 Agent도 붙일 수 있다.

모델이 이미 schema대로 채웠는데, 왜 JSON을 직접 검증하는가?

모델이 채운 파라미터는 느슨한 제약이다. arguments는 문자열인 경우가 많고, 필드가 빠지거나, 타입이 틀리거나, 선언하지 않은 키가 더해질 수 있다. 프로덕션에서는 여전히 parse + JSON Schema로 검증한 뒤 업무 층에 넘긴다. Codex의 --output-schema도 최종 답만 묶을 뿐, 매 단계 tool 결과 검사를 대체하지 않는다.

Xcode 27 Agent는 Apple 모델만 쓰는가?

아니다. Xcode 27은 Anthropic, Google, OpenAI의 모델과 Agent를 같은 에디터 워크플로에 잇고, 로컬 모델도 지원한다. ACP로 외부 Agent를, MCP로 외부 도구를 붙일 수 있다. 바뀌는 것은 도구 상자와 검증 수단이지, 루프 자체가 아니다.

정리

세 제품의 화면은 계속 채팅처럼 자랄 것이다. 밑의 문장은 바뀌지 않았다:

Coding Agent = 모델 결정 × Tool Calling × harness 실행. JSON은 도구 파라미터와 회신 결과의 공통 형태다.

먼저 루프를 보고, 그다음 도구 상자를 고른다. Claude Code는 일반 Agent를 강화하고, Codex는 샌드박스와 이벤트를 다루며, Xcode 27은 빌드와 Preview를 검증 도구로 만든다. schema는 선언에 쓰고, 검증은 실행 층에 두며, 디버깅은 브라우저 로컬에 남겨도 된다.

다음: 실패한 tool call을 JSONNote에 붙인다

← 블로그로