Agent SDK의 승인과 세션 제어
추정한 제어 메시지 대신 공개 옵션 사용하기
섹션 제목: “추정한 제어 메시지 대신 공개 옵션 사용하기”Agent SDK는 호스트가 비공개 JSON 메시지를 직접 만들어 CLI에 보내는 방식으로 문서화되어 있지 않다. 공식 SDK는 query() 옵션, 권한 콜백, 스트리밍 메시지로 에이전트의 행동을 제어한다. 따라서 initialize, set_model, get_context_usage 같은 임의의 제어 메시지나 응답 스키마를 애플리케이션 계약으로 삼아서는 안 된다.
애플리케이션 → prompt + Options → Agent SDK │ 도구 제안 ── 권한 정책·사용자 승인 │ 메시지 스트림 ← 도구 결과·최종 result승인 요청과 AskUserQuestion 같은 상호작용은 하나의 query 호출 안에서 진행된다. 애플리케이션은 승인 정책을 구성할 때 명령어·경로·MCP 서버별로 최소 권한을 적용하고, 사용자가 이해할 수 있는 승인 UI와 거부 경로를 제공해야 한다. 자동 승인 규칙은 신뢰하는 고정 작업공간의 읽기 전용 도구부터 좁게 추가하는 것이 안전하다.
세션의 세 가지 선택
섹션 제목: “세션의 세 가지 선택”세션은 프롬프트, 도구 호출, 도구 결과, 응답으로 이루어진 대화 기록이며 SDK가 기본적으로 디스크에 저장한다. 세션은 대화 맥락을 보존할 뿐 파일 시스템의 스냅샷은 아니다. 파일 변경을 되돌리려면 별도의 파일 체크포인팅 또는 버전 관리 절차가 필요하다.
| 목표 | TypeScript 옵션 | 의미 | | --- | --- | --- | | 같은 디렉터리의 가장 최근 대화 이어가기 | continue: true | 세션 ID를 앱이 관리하지 않아도 된다 | | 특정 과거 대화로 돌아가기 | resume: sessionId | 다중 사용자·다중 작업에 적합하다 | | 대화 이력의 대안을 탐색하기 | resume + forkSession: true | 원본 이력은 유지하고 새 세션을 만든다 | | 대화 기록을 저장하지 않는 단발 작업 | persistSession: false | TypeScript에서 호출 기간 동안만 메모리에 둔다 |
세션 ID 캡처와 재개
섹션 제목: “세션 ID 캡처와 재개”최종 result 메시지에는 session_id가 포함된다. 애플리케이션은 이를 사용자·작업 식별자와 함께 안전한 저장소에 보관한 뒤, 후속 작업에 resume 옵션으로 전달할 수 있다. 한 디렉터리에서 대화 하나만 관리한다면 continue: true가 더 단순하다.
import { query } from "@anthropic-ai/claude-agent-sdk";
let sessionId: string | undefined;
for await (const message of query({ prompt: "auth 모듈을 분석해 주세요.", options: { allowedTools: ["Read", "Glob", "Grep"] }})) { if (message.type === "result") { sessionId = message.session_id; }}
for await (const message of query({ prompt: "앞선 분석에서 제안한 첫 번째 수정만 구현해 주세요.", options: { resume: sessionId, allowedTools: ["Read", "Edit", "Write"] }})) { if (message.type === "result" && message.subtype === "success") { console.log(message.result); }}세션 ID는 대화 기록에 접근하는 키이므로 로그에 무분별하게 노출하지 않는다. 프로세스 재시작이나 다른 호스트로 옮기는 경우에는 공식 SessionStore 방법 또는 애플리케이션의 명시적인 결과 저장을 검토한다. 같은 대화 이력을 분기해도 작업 디렉터리가 공유되면 파일 변경은 서로 보일 수 있다는 점도 반드시 함께 설계해야 한다.