
AI로 풀어보는 AI-DLC v2: 진행의 핵심
요약
AI-DLC v2의 핵심 설계 원칙인 엔진(Engine)과 컨덕터(Conductor)의 분리 구조를 분석합니다. 결정론적 엔진이 다음 단계를 지시하고 LLM 컨덕터가 이를 실행함으로써, 에이전트의 일탈을 방지하고 재현성과 세션 재개 가능성을 확보하는 방법을 설명합니다.
핵심 포인트
- 결정론적 엔진과 LLM 컨덕터의 역할 분리를 통한 안정성 확보
- 엔진은 상태를 읽고 타입 지정된 지시(Directive)만 반환
- 컨덕터는 LLM을 통해 실제 실행 및 대화 문맥 관리 수행
- 상태 외재화를 통해 대화 중단 시에도 작업 재개 가능
- LLM의 비결정성을 제어하여 진행 과정의 재현성 보장
본 기사의 위치— 본 기사는 awslabs/aidlc-workflows 리포지토리의 규범 규칙 및 이용 가이드를 소재로 하여, 필자가 AI를 활용해 읽어내고 정리한 해석입니다. AWS가 공식적으로 발표한 방법론이 아니며, 1차 자료의 번역·요약도 아닙니다.
시리즈— 본 기사는 AI로 풀어보는 AI-DLC v2 시리즈의 일부입니다.
참조한 버전— Claude Code 구현을 대상으로, 2026년 6월 시점의 v2.1.3 (커밋 c95070e, core/)를 참조하고 있습니다. Kiro·Codex 구현은 대상에서 제외되며, 기술 내용이 다를 수 있습니다. OSS 구현은 업데이트가 계속되고 있으므로, 최신 상태는 공식 리포지토리를 확인해 주세요.
개요
AI-DLC v2의 진행은 성질이 다른 두 주체가 분담하여 수행합니다. 상태를 읽고 다음 수를 결정하는 결정론적 (Deterministic) 엔진과, 그 수를 실제로 움직이는 AI 컨덕터 (Conductor)입니다. 엔진은 "다음에 무엇을 해야 하는가"를 하나의 타입 지정된 지시 (Directive)로서 반환할 뿐, 에이전트를 기동하거나 사람에게 묻지 않습니다. 실행은 모두 컨덕터가 맡습니다.
이러한 분리가 있기에 진행은 대화의 흔들림에 좌우되지 않고, 동일한 상태라면 동일한 순서로 재현할 수 있으며, 세션이 끊겨도 이어서 재개할 수 있습니다. 본 기사에서는 지시의 전체 모습과, 질의와 보고를 왕복하는 제어 루프(Control Loop), 그리고 결정론을 관철하는 설계가 유일하게 완화되는 지점을 읽어냅니다.
엔진과 컨덕터의 분리
진행의 핵심에는 성질이 다른 두 주체가 있습니다.
| 엔진 | 컨덕터 |
|---|---|
| 정체 | 결정론적 코드 (aidlc-orchestrate.ts) |
| 역할 | "다음에 무엇을 해야 하는가"를 타입 지정된 지시 1개로 답변 |
| 상태 | 가지지 않음. 매번 파일을 다시 읽음 |
| 하지 않는 것 | 에이전트를 기동하지 않음 · 사람에게 직접 질문하지 않음 · 일탈을 만들지 않음 |
엔진은 상태 파일 (aidlc-state.md)과 컴파일된 스테이지 그래프 (stage-graph.json)를 읽고, 하나의 지시 (JSON)를 반환하고 멈춥니다. 질의 커맨드 next는 상태를 전혀 바꾸지 않는 읽기 전용입니다. 엔진은 사람에게 묻는 도구를 가지지 않으며, 에이전트도 기동하지 않습니다. 판단만을 반환하고, 실행은 모두 컨덕터에게 위임합니다.
판단을 매번 엔진에 의뢰하는 이유
컨덕터는 똑똑한 LLM입니다. 그렇다면 "다음은 요구사항 분석, 그다음은 설계"라고 스스로 진행하면 될 것처럼 보입니다. 그럼에도 굳이 매번 엔진에게 물으러 가게 하는 것은 세 가지 보장을 위해서입니다.
- 일탈 방지— LLM에 맡기면 긴 대화 도중에 단계를 건너뛰거나, 요청받지도 않은 스테이지로 탈선하기도 합니다. 다음 수를 결정론적 코드로 고정하면, 진행이 대화의 흔들림에 좌우되지 않습니다.
- 재현성— 엔진은 동일한 상태와 동일한 그래프라면 반드시 동일한 지시를 반환합니다. 판단에 LLM의 비결정성 (Non-determinism)이 섞이지 않으므로, 진행을 재현할 수 있습니다.
- 세션을 넘나드는 재개— 엔진은 세션의 기억을 가지지 않습니다. 진행 상황은 모두 상태 파일에 있으며, 엔진은 매번 그것을 다시 읽어 판단합니다. 대화가 끊겨도, 다른 대화에서 시작하더라도, 상태 파일만 있다면 이어서 올바르게 재개할 수 있습니다.
"기억을 가지지 않는다"는 것은 약점이 아니라, 재현성과 재개 가능성을 성립시키는 전제입니다. 상태가 코드 내부가 아닌 파일로 외재화되어 있기 때문에, 엔진은 일회용으로 사용할 수 있으며 몇 번을 호출해도 동일한 답을 반환할 수 있습니다. (상태 파일과 감사 로그의 내용은 별도 기사 「상태와 감사」에서 다룹니다.)
엔진 고유의 두 가지 작업
엔진 내용의 대부분은 기존의 결정론적 도구들을 조합하고 있을 뿐입니다. 그래프 읽기, 다음 스테이지 산출, 스코프 이름 검증. 모두 기존의 도구 함수를 호출합니다. 엔진이 독자적으로 담당하는 것은 단 두 가지뿐입니다.
- 결정 규칙— "관측된 상태와 그래프"를 "지시의 종류"로 옮기는 판단
- 산출물 경로 해결— 그래프가 가진 어휘 이름을, 액티브 인텐트 (Active Intent)의 기록 디렉토리 하위의 실제 경로로 변환하는 문자열 조립
둘 다 순수한 결정론적 코드입니다. 소스 코드의 주석 (aidlc-orchestrate.ts)은 이 경계선을 다음과 같이 단언합니다.
라우팅(routing) 문자열 빌딩을 LLM에게 맡긴다면 이 논지 전체가 뒤집힐 것입니다.
(ルーティングの文字列組み立てを LLM にやらせたら、この思想全体がひっくり返る)
무엇을 해야 하는지에 대한 지식 작업은 컨덕터(Conductor, LLM)가, 다음 어느 스테이지를 수행할지에 대한 라우팅(routing)은 엔진(Engine, 도구)이 담당합니다. 이러한 역할 분담이 설계 사상의 핵심입니다.
9종의 지시
엔진과 컨덕터를 연결하는 것이 지시(directive)입니다. aidlc-directive.ts에 정의된 고정된 인터페이스로, 엔진과 컨덕터가 동일한 하나의 파일을 import 합니다. 따라서 양자 사이의 '상호작용 형태'가 어긋날 리가 없습니다. 지시의 정의 그 자체는 상태를 가지지 않고, 아무것도 발행(emit)하지 않으며, I/O도 하지 않는 순수한 계약(contract)입니다. 엔진은 지시를 구성하고 검증한 뒤 출력하며, 컨덕터는 이를 받아 검증한 뒤 읽습니다. 잘못된 지시는 묵인되지 않고 그 자리에서 에러가 발생합니다.
지시의 종류는 총 9종입니다. 각각이 '무엇을 지시할지'를 소스 코드의 타입 정의(type definition)로부터 도출합니다.
| kind | 무엇을 지시하는가 |
|---|---|
run-stage | lead·support 에이전트를 로드하고, consumes (입력 결과물)를 읽고, 스테이지 본체를 실행하며, produces (출력)를 쓰고, memory.md를 유지함 |
dispatch-subagent | run-stage와 동일하지만, 스테이지를 Task로 이름이 지정된 worker에게 던져 실행함 |
invoke-swarm | 구축 배치를 N개의 작업 복사본(worktree)에 N명의 worker로서 병렬로 전개함 |
present-gate | 학습 게이트(learning gate)를 돌린 후 승인 게이트(approval gate)를 묘사함 |
ask | 구조화된 질문을 묘사함 (재개 선택·스코프 확인·자율 사다리) |
print | 문구를 그대로 표시하고 멈춤 (상황 표시나 도움말) |
error | 에러를 표시하고 멈춤 |
done | 루프를 멈춤 (워크플로 완료 또는 단일 스테이지 완료) |
parked | 장기 워크플로를 현재의 스테이지 경계에서 일시 정지(park)하여 종료함 (후술) |
이 9종 중 현재 엔진이 실제로 발행하는 것은 7종입니다. next 핸들러는 run-stage / invoke-swarm / ask / print / error / done + parked를 발행하며, 남은 present-gate / dispatch-subagent 2종은 "후속 구현 단계(wave)에서 구현한다"고 명시하며 제외합니다. 이 2종은 결함이 아니라, 타입으로는 고정된 계약에 포함하되 단계적으로 구현하는 과정에 있는 것으로 정의합니다.
run-stage가 운반하는 것
발행되는 지시 중 압도적 다수를 차지하는 것이 run-stage입니다. 이는 단순히 "이 스테이지를 수행하라"는 의미를 넘어, 스테이지 실행에 필요한 라우팅 세트를 컨덕터가 재도출(re-derive)할 필요가 없는 형태로 운반합니다.
lead_agent/support_agents— 주 담당(Lead) 및 보조 에이전트mode—inline/subagent/agent-teamgate— 승인 게이트를 설치할지 여부 (후술할 예외를 제외하고는 불리언(boolean) 값)rules_in_context— 이 스테이지에서 적용되는 규칙의 해결된 경로(resolved path)sensors_applicable— 적용 가능한 센서의 IDconsumes/produces— 입출력 결과물의 해결된<record>/...경로reviewer?/reviewer_max_iterations?— 리뷰어를 선언하는 스테이지에만 붙음conductor_persona?— 워크플로의 첫 번째run-stage에만 삽입되는 실행 품질을 결정하는 페르소나 (후술)unit?— per-unit 구축 스테이지에서 엔진이 해결한 구체적인 작업 단위명. 작업 단위마다run-stage를 돌리는 반복(iteration)의 1회차임을 나타내는 표식이며, 커버되지 않은 작업 단위에서는 게이트가 억제됨
규칙(Rule, 따를 의무가 있는 제약)은 지시사항에 동봉되어 전달되는 반면, 지식(Knowledge, 참조용 수법)은 지시에 포함되지 않고 컨덕터(Conductor)가 실행 시점에 직접 읽으러 갑니다. 이러한 비대칭성도 run-stage 설계에 나타나 있습니다. 규칙과 지식의 차이는 별도 기사 「규칙과 지식」에서, unit?의 per-unit 해결은 별도 기사 「성과물의 흐름」에서 다룹니다.
단 한 번 전달되는 실행 인격
컨덕터의 「스테이지를 원활하게 돌리기 위한 실행 품질」에 대한 마음가짐은 aidlc-common/conductor.md에 단 한 번 작성되어 있습니다. 스킬(Skill)은 이 파일을 경로 참조하지 않습니다. 대신 엔진이 내용을 읽어 워크플로우의 첫 번째 run-stage 지시에 매립하여 전달합니다. 이후의 지시에는 포함되지 않습니다 (인격은 세션 내에서 지속되기 때문입니다). 어디서 시작하더라도 동일한 컨덕터 인격이 추가 설정 없이 전달되는 구조입니다.
제어 루프
이것들을 연결하면 진행은 다음과 같은 제어 루프가 됩니다.
컨덕터에게만 맡겨두면 문의 자체를 잊고 탈선할 수 있기 때문에, done이 반환될 때까지 이 루프를 계속하게 만드는 메커니즘(포워딩 루프(Forwarding Loop)의 Stop 후크)이 별도로 존재합니다. 엔진이 반환하는 지시는 「아직 맡고 있는 작업」으로서만 표현되므로, 설령 엔진이 고장 나더라도 허가된 작업을 계속할 수 있을 뿐 세션을 탈취할 수는 없습니다.
보고 사이클
엔진에 대한 문의인 next가 상태를 읽는 것에 반해, report는 결과를 다시 씁니다. 컨덕터가 지시된 한 수를 실행 완료하면 report로 결과를 보고하고, 그에 따라 상태가 전진하며 다음 next가 새로운 상태를 읽습니다. 이것이 보고 사이클입니다.
report 자체는 전이 로직을 가지지 않습니다. aidlc-state.ts의 전이 서브 커맨드(subcommand)로 향하는 디스패처(dispatcher) 역할에 충실하며, 「게이트 상태 → 종료 여부」 순서로 어떤 서브 커맨드에 위임할지를 결정합니다.
| 보고한 스테이지의 상태 | 위임 대상 | 발생하는 일 |
|---|---|---|
| 게이트 있음 | approve | GATE_APPROVED와 STAGE_COMPLETED를 출력하고, approve가 전진(비종료라면 advance, 종료라면 complete-workflow)까지 모두 호출함 |
| 게이트 없음·비종료 | advance | 다음 진행 중인 스테이지로 전진함 |
| 게이트 없음·종료 | complete-workflow | PHASE_COMPLETED, PHASE_VERIFIED, WORKFLOW_COMPLETED를 출력하며 마무리함 |
게이트의 유무는 next가 run-stage의 gate를 결정하는 것과 동일한 축입니다. 부트스트랩(Bootstrap) 초기화 스테이지만이 자동으로 진행되며, 그 외의 모든 스테이지는 게이트를 설치합니다.
approve는 전이의 전체를 소유합니다. 승인은 감사 이벤트(audit event)를 출력한 후 전진까지 한 번에 처리하므로, 승인 후에 advance를 별도로 호출해서는 안 됩니다. 만약 승인 전에 게이트 시작 기록이 누락되었더라도, report가 누락된 게이트를 보완한 후 승인합니다. 감사 로그 발행은 툴이 소유하며, 상태 전이 서브 커맨드가 내부에서 올바른 감사 이벤트를 발행합니다. 컨덕터가 수동으로 감사 행을 작성하는 일은 없습니다. 승인 게이트의 사람 측 절차(반려 왕복이나 「현 상태로 승인」)는 별도 기사 「승인 게이트」에서, 감사 이벤트 체계는 별도 기사 「상태와 감사」에서 다룹니다.
park — 엔진의 세 번째 서브 커맨드. next(읽기) / report(쓰기)에 park가 추가되었습니다. 장기(enterprise 스코프 등) 워크플로우를 스테이지를 공승인(empty approval)으로 소모하여 done에 도달하게 하지 않고, 현재 스테이지 경계에서 일시 정지합니다. aidlc-orchestrate.ts park는 aidlc-state.ts park에 위임하여 일시 정지 마커를 배치하고(변이는 툴 측에서 수행하며 엔진은 읽기 전용을 유지), 종료 상태인 parked 지시를 내립니다. 이후의 순수한 next는 parked를 반환하며, Stop 후크가 이를 허용하여 턴을 깔끔하게 종료합니다. /aidlc --resume으로 재개합니다. 또한 자율 모드 구축 시에는 park
거부됩니다(무인 루프는 중단하지 않습니다). 이와 함께, 선언된 산출물이 디스크에 없는 스테이지를 완료할 수 없도록 하는 아티팩트 가드(Artifact Guard)도 있습니다(빈 승인 방지. 자세한 내용은 별도 기사 「승인 게이트(Approval Gate)」 참조).
다음 스테이지가 결정되는 방식
next가 "다음은 무엇인가"를 답하는 토대(foundation)는 스테이지 그래프(stage graph)입니다. 그래프는 구조적인 진실이며, 스테이지 정의의 전체와, 그것들이 선언하는 requires_stage / produces / consumes 에지를 합친 것이 완전한 DAG(Directed Acyclic Graph, 사이클이 없는 유향 그래프)가 됩니다. 이는 YAML로부터 stage-graph.json으로 컴파일됩니다.
- 스코프(Scope)는 서브 DAG— 스코프(feature, bugfix, poc 등)는 그래프에서 잘라낸 부분 그래프(subgraph)입니다. 각 스테이지의 프론트매터(frontmatter, 파일 도입부의 메타 정보)에 있는
scopes:를 전치(transpose)한 EXECUTE 그리드 중, EXECUTE에 해당하는 스테이지와 그 사이의requires_stage에지를 잘라냅니다. 스코프가 "어떤 스테이지를 실행할지"를 결정합니다. - 직렬 런타임(Serial Runtime)은 번호 순으로 선형화— 각 서브 DAG를 번호 순으로 나열하여 반복합니다. 이 번호 순서는 의존 관계를 깨뜨리지 않는 방식(Topological Sort, 위상 정렬)으로서 타당하게 구성되어 있습니다.
- 다음 스테이지 산출—
nextInScopeStage가 스코프 내에서 현재 스테이지 다음에 오는 EXECUTE 스테이지를 반환합니다. 상태 파일의 덮어쓰기(개별적인 EXECUTE/SKIP 지정이나 기존 체크박스)도 고려합니다.
5페이즈 32스테이지와 스코프별 실행 범위는 별도 기사 「공정과 에이전트」에서, 스코프의 메커니즘은 별도 기사 「스코프」에서 다룹니다.
산출물 경로(Artifact Path)의 해결
컴파일된 그래프는 산출물을 어휘 이름(vocabulary name)으로 가집니다(produces는 단순 이름의 배열, consumes는 조건부 배열). 컨덕터(Conductor)는 실제 경로(actual path)로 동작해야 하므로, 엔진이 발행 시점에 이름으로부터 경로를 해결(resolve)하며, 컨덕터에게 재도출(re-derive)하게 하지 않습니다. 이 부분이 엔진이 독자적으로 담당하는 또 다른 업무입니다. 해결 규칙 자체(소비물은 생산자 디렉토리에 존재, conditional_on을 Project Type으로 떨어뜨림, per-unit 스테이지에 작업 단위 이름을 주입함)는 별도 기사 「산출물의 흐름」에서 다룹니다. 본 기사는 "엔진이 결정론적으로 해결한다"라는 역할 분담에만 집중합니다.
결정론의 유일한 예외
지금까지의 원칙은 "다음 단계는 모두 엔진이 결정론적으로 결정한다"였습니다. 이 원칙이 유일하게 깔끔하게 깨지는 지점이 있으며, 그것이 이 설계 사상을 가장 잘 보여줍니다.
gate는 거의 항상 불리언(boolean) 값입니다. 스코프의 스테이지 맵이 "이 스테이지가 게이트를 설치할 것인가"를 결정론적으로 답하기 때문에, 엔진은 순수한 불리언 값을 발행합니다. 단 하나의 예외는, 구축의 첫 번째 Bolt(최소한의 End-to-End를 통과하는 첫 번째 실행 단위)의 게이트입니다. 이것은 팀의 자유 기술 산문(prose)으로부터 "스탠스(stance)"를 읽어내어 결정되지만, 영어 산문을 스탠스로 변환하는 파서(parser)는 존재하지 않습니다. 엔진은 이를 결정론적으로 풀 수 없습니다.
따라서 엔진은 보류합니다. gate: "unresolved"라는 센티널 값(sentinel value, 결정 불가능의 표시)을 내보내며 멈추고, 컨덕터가 산문을 분류하여 타입이 지정된 스탠스를 report --skeleton-stance로 반환하면, 다음 next가 확정된 게이트를 발행합니다.
결정적인 점은, 돌아오는 것이 타입이 지정된 스탠스뿐이라는 것입니다. 엔진은 전이(transition)의 소유권을 놓지 않으며, 자유로운 영어가 판단으로서 엔진으로 흘러 들어오는 일은 없습니다. 이 설계가 결정론적인 이유는 "불리언 값이 갈리기 때문"이 아니라 "산문을 타입이 지정된 스탠스로 분류했기 때문"입니다. 스탠스의 3가지 값과 그 의미, 산문의 분류 절차, practices에 의한 덮어쓰기는 별도 기사 「워킹 스켈레톤(Walking Skeleton)」에서 다룹니다. 본 기사에서는 엔진이 보류하고 타입이 지정된 값만을 받는 메커니즘까지만 다룹니다.
이것은 핵심 설계 사상의 축소판입니다. 지식 작업(자유로운 산문의 해석)은 LLM이, 라우팅(다음에 무엇을 실행할지)은 도구가 담당하며, 양자의 경계를 타입이 지정된 단 하나의 값만이 넘나듭니다. 판단을 매번 엔진에 요청하는 것도, 이 지점에서 예외적으로 LLM에게 판단을 넘기는 것도, 동일한 하나의 선긋기의 양면입니다.
참조 원문
| 파일 | 내용 |
|---|---|
tools/aidlc-directive.ts | 지시(Directive)의 동결 계약. 9종의 kind 판별 공용체(Union Type)·각 필드·런타임 검증. "engine↔conductor 간의 동결 인터페이스", "상태 없음·I/O 없음의 순수 계약", GATE_UNRESOLVED 센티널(Sentinel) 정의 |
tools/aidlc-orchestrate.ts | 엔진 본체. next (읽기 전용 질의)·report (전이의 커밋)·park. "추가되는 것은 결정 규칙과 경로 해결(Path Resolution) 두 가지", present-gate / dispatch-subagent를 발행하지 않는 핸들러, skeleton round-trip, report의 게이트→종단 디스패치(Dispatch) |
tools/aidlc-graph.ts | 스테이지 그래프(Stage Graph) 라이브러리. "그래프는 구조적 진실 = DAG", "스코프는 서브 DAG (EXECUTE 슬라이스 + requires_stage 에지)", "직렬 런타임은 번호 순으로 선형화" |
tools/aidlc-state.ts | 상태의 읽기/쓰기 및 전이 서브 커맨드 (advance / approve / reject / complete-workflow / park 등). report가 위임하는 대상. 감사(Audit) 발행은 이들이 내부적으로 소유 |
aidlc-common/conductor.md | 컨덕터(Conductor)의 실행 품질 인격. 엔진이 첫 번째 run-stage 지시에 임베딩하여 전달 |
aidlc-common/protocols/stage-protocol.md | 승인 게이트·완료 메시지와 report 흐름·상태 추적 (감사는 툴 소유·추가 전용) |
CHANGELOG.md | 타입 지정 지시 계약·report · conductor.md 인격 임베딩(전달)·skeleton round-trip·parked / park 및 아티팩트 가드(Artifact Guard) 도입 |
관련 기사
이전 기사: 공정과 에이전트
다음 기사: 스코프
목차: AI로 풀어보는 AI-DLC v2
Discussion

AI 자동 생성 콘텐츠
본 콘텐츠는 Zenn AI의 원문을 AI가 자동으로 요약·번역·분석한 것입니다. 원 저작권은 원저작자에게 있으며, 정확한 내용은 반드시 원문을 확인해 주세요.
원문 바로가기