자신의 API에 임베드할 수 있는 Claude Code 스타일의 하네스를 만들었습니다
요약
에이전트가 호스트 시스템에 영향을 주지 않고 안전하게 도구를 사용할 수 있도록 설계된 샌드박스형 런타임 'ork'를 소개합니다. 인프로세스 가상 파일 시스템과 POSIX 스타일 셸을 통해 메모리 내에서 실행되며, 스냅샷과 결정론적 테스트가 가능합니다.
핵심 포인트
- 인프로세스 가상 파일 시스템을 통한 안전한 샌드박스 환경 제공
- 파이프, 리다이렉션 등을 지원하는 실제 POSIX 스타일 셸 구현
- 세션 상태를 바이트 단위로 저장하고 복구할 수 있는 무료 스냅샷 기능
- Hono 기반의 HTTP API를 통한 서버 기능 및 테넌트 격리 지원
- 부작용 없는 엔드 투 엔드 결정론적 테스트 가능
에이전트 기능을 구축하면서 저는 계속해서 동일한 문제에 부딪혔습니다. 모델에게 실제 도구들 — bash, 파일 편집(file edits), grep — 를 제공하고 싶지만, 모델이 호스트 시스템 근처에 접근하는 것은 원치 않으며, 세션마다 컨테이너나 VM(가상 머신)을 실행하는 것은 무겁고 느리며 스냅샷(snapshot)을 찍기도 매우 번거롭다는 점입니다.
그래서 저는 ork를 만들었습니다: 샌드박스 전체가 하나의 데이터 구조인 샌드박스형 에이전트 런타임(sandboxed agent runtime)입니다. 모델은 Claude Code가 가진 것과 동일한 6가지 도구(Bash, Read, Write, Edit, Glob, Grep)를 갖게 되지만, 이 도구들은 제가 처음부터 작성한 인프로세스 가상 파일 시스템(in-process virtual filesystem)과 POSIX 스타일의 셸(lexer → parser → interpreter)을 대상으로 실행됩니다. 디스크도, child_process도, 네트워크도 없습니다. 에이전트는 말 그대로 사용자의 기계에 손을 댈 수 없습니다.
이를 통해 얻을 수 있는 이점은 다음과 같습니다:
- 장난감이 아닌 실제 셸(shell): 파이프(Pipes), 글로브(globs), 리다이렉션(redirections), 헤레독(heredocs), for 루프 등을 지원합니다. 에이전트는 방금 작성한 파일들에 대해 awk 스타일의 파이프라인을 실행할 수 있으며, 이 모든 것은 메모리 내에서 해석됩니다.
- 무료 스냅샷: 전체 세션(파일 시스템(FS) + 대화)이 인프로세스 상태(in-process state)이므로, 콘텐츠 주소 지정 저장소(content-addressed store)에 스냅샷을 찍고 바이트 단위로 완벽하게 복구할 수 있습니다. 에이전트를 일시 중지하고 다음 주에 재개하거나, 포크(fork)할 수 있습니다.
- 서버 기능 포함: SSE 스트리밍, Bearer 인증, 테넌트별 격리(per-tenant isolation), 세션별 턴 잠금(per-session turn locks)을 지원하는 Hono HTTP API를 제공합니다. POST /v1/sessions를 통해 프롬프트를 보내고, tool_call / tool_result 이벤트가 스트리밍되는 것을 확인할 수 있습니다.
- 결정론적 테스트(Deterministic testing): 호스트에 아무런 영향을 주지 않기 때문에, 전체 스택 — HTTP → 세션 관리자(session manager) → 에이전트 루프(agent loop) → 도구(tools) → 셸(shell) → VFS → 스냅샷 — 이 스크립트된 모의(mock) 모델과 함께 엔드 투 엔드(end-to-end)로 실행됩니다. 500개 이상의 테스트를 부작용(side effects) 없이 수행할 수 있습니다.
간단한 예시:
const session = createSession({
model: "anthropic/claude-sonnet-4.5",
files: { "/workspace/data.csv": "name,score\nAlice,91\nBob,72\n" },
});
for await (const ev of session.send("Compute the average score and write summary.md")) {
if (ev.type === "tool_call") console.log(ev.tool, ev.input);
}
const { snapshotId } = await session.snapshot(store); // 언제든 재개 가능
명백한 트레이드오프(tradeoff): 완전한 Linux 유저랜드(userland)는 아닙니다.
그 안에서 npm install을 하거나 C를 컴파일할 수는 없습니다 — 가상 파일 시스템 (FS) 상에서 내장 명령어를 사용하는 POSIX 스타일의 셸 (POSIX-ish shell)이기 때문입니다. "파일을 읽고/변환하고/쓰며 작업을 수행하기 위해 스크립트를 작성하는 에이전트"에게는 그것만으로도 충분하며, 이것이 세션 생성이 거의 무료이고 스냅샷을 찍을 수 있는 이유입니다. 만약 실제 프로세스 (real processes)가 필요하다면, 여전히 Firecracker이나 컨테이너 (containers)를 사용해야 합니다. TypeScript를 사용하며, AI SDK를 통해 모델에 구애받지 않습니다 (Anthropic 직접 연결 또는 게이트웨이를 통한 모든 제공업체).
리포지토리 (Repo): https://github.com/GitHamza0206/ork
가차 없는 피드백을 환영합니다 — 특히 에이전트 샌드박싱 (agent sandboxing)을 다른 방식으로 해결하신 분들의 의견을 듣고 싶습니다. 여러분의 사용 사례에서 인메모리 (in-memory) 방식이 어디에서 한계에 부딪히는지 궁금합니다.
제출자: /u/Outside-Project-1451
[링크] [댓글]
AI 자동 생성 콘텐츠
본 콘텐츠는 r/ClaudeAI의 원문을 AI가 자동으로 요약·번역·분석한 것입니다. 원 저작권은 원저작자에게 있으며, 정확한 내용은 반드시 원문을 확인해 주세요.
원문 바로가기