스튜어트 펠드먼이 1976년에 옳았던 이유: AI 에이전트에게는 매니페스트 파일(Makefile)이 필요하지, 20단계 프롬프트가 아니다
요약
본 글은 AI 코딩 에이전트가 단순히 단계별 체크리스트(프롬프트 엔지니어링)를 따르는 방식의 한계를 지적합니다. LLM은 복잡한 절차적 상태 전이와 조건부 점프(GOTO)를 신뢰성 있게 처리하기 어렵습니다. 대신, 시스템 아키텍처처럼 '무엇이 무엇에 의존하는지' 관계를 정의하는 매니페스트 파일(Makefile) 방식의 인지 구조가 필요하다고 주장합니다.
핵심 포인트
- AI 에이전트는 선형 체크리스트보다 복잡한 종속성 관리가 필수적입니다.
- LLM은 긴 대화 기록에서 주의력 저하와 맥락 상실을 겪기 쉽습니다.
- 명령형 GOTO 점프는 LLM에게 신뢰하기 어려운 구조입니다.
- Makefile처럼 시스템의 의존성을 정의하는 아키텍처가 핵심입니다.
스튜어트 펠드먼의 1976년 벨 연구소 발명이 현대 AI 코딩 에이전트가 놓치고 있던 정확한 인지 아키텍처입니다.
"소프트웨어 작성에서 발생하는 문제 대부분은 무엇이 무엇에 의존하는지 모르는 것에서 비롯된다."
— 스튜어트 펠드먼(Stuart Feldman),
make의 창시자 (1976)
1. 프롬프트 엔지니어링 함정: 단계별 체크리스트가 주는 매혹적인 착각
거의 모든 사람이 자율 코딩 에이전트를 동일한 방식으로 설계합니다. 시스템 프롬프트나 SKILL.md 파일 안에 번호가 매겨진 체크리스트를 넣는 것입니다.
Step 1: 트래커에서 열린 이슈를 선택한다.
Step 2: 코드베이스를 읽고 아키텍처 계획을 작성한다.
Step 3: 잠시 멈추고 인간의 승인을 요청한다.
...
종이 위에서는 놀라울 정도로 체계적으로 보입니다. 마치 첫날 신입 인턴에게 건네주는 표준 운영 절차서(Standard Operating Procedure) 같습니다.
하지만 실제 작동 환경에서는, 이 체크리스트는 믿을 수 없을 만큼 혼란에 빠집니다.
실패 모드: 사전 학습 중력과 명령형 GOTO 스파게티
대규모 언어 모델(Large Language Models)은 확률적 다음 토큰 예측기입니다. 20단계의 선형 체크리스트는 절차적 상태 전이(procedural state transitions)의 조합 폭발을 만듭니다.
대화 기록이 컴파일러 로그, 테스트 출력, git diff 등으로 채워지면서, 모델은 **주의력 저하(attentional degradation)**를 경험합니다. 체크리스트의 상단 부분이 수만 토큰 전으로 흘러갑니다.
더 심각한 것은 **명령형 GOTO 함정(Imperative GOTO Trap)**입니다. 6단계에서 테스트가 실패하거나, 자동 코드 검토 봇이 9단계 이후에 세 개의 코멘트를 남기면 어떻게 될까요?
프롬프트 작성자는 고통스럽고 명령적인 라우팅 규칙을 작성하기 시작합니다:
"검토 봇이 9단계 이후에 코멘트를 남기면, 12.2단계로 이동하라. 코드 수정이 필요하면 5단계로 돌아가라. 하지만 1단계에서 브랜치를 다시 만들지 말고, 8단계로 진행하되 새로운 PR을 생성하지 말고, 그냥 lease를 붙여 push하고 12.4단계로 돌아가라..."
LLMs는 150턴에 걸친 도구 사용 과정(tool turns) 전반에 걸쳐 중첩된 루프 카운터와 조건부 GOTO 점프를 가진 명령형 가상 머신(imperative virtual machine)을 신뢰성 있게 시뮬레이션할 수 없습니다. 이들은 위치를 잃거나, 중간 게이트를 건너뛰거나, 순수한 맥락적 피로(contextual fatigue) 때문에 종료 조건을 환각(hallucinate)합니다.
flowchart TD
S1["Step 1: Pick Issue"] --> S2["Step 2: Write Plan"]
S2 --> S5["Step 5: Code & Test"]
...
"중간에 재개하기"의 재앙 (The "Resuming in the Middle" Disaster)
에이전트가 풀 리퀘스트(pull request)를 열고, CI(Continuous Integration)가 실행되는 동안 일시 정지된 상태에서, 2시간 후에 다음과 같은 메시지와 함께 깨어난다면 어떻게 될까요?: "위젯 테스트(widget test)에서 CI가 실패했고 리뷰 봇이 리팩토링을 제안했어."
- 선형 체크리스트 에이전트(linear checklist agent)는 스킬 파일(skill file) 상단에 있는
Step 1: Pick an open issue를 읽고 환각하기 시작하거나, 어떤 티켓으로 작업할지 물어보거나, 처음부터 고대 유적 발굴을 다시 시작합니다. - 인간 운영자(human operator)는 마이크로매니징(micro-management) 상태로 되돌아가야 합니다: "아니, 티켓을 고르지 마. 너는 Step 12의 Sub-step B에 있어—테스트를 수정하고 푸시해!"
2. 벨 연구소의 깨달음: make는 결코 C 파일 전용이 아니었다
1976년 Bell Laboratories에서 Stuart Feldman은 이와 정확히 같은 시스템 문제, 즉 종속성 추적(dependency tracking)과 상태 조정(state reconciliation) 문제를 해결했습니다.
Feldman은 다음과 같은 명령형 셸 스크립트(imperative shell script)를 작성하지 않았습니다:
"먼저 foo.c를 컴파일하고, 다음으로 bar.c를 컴파일한 후, 이들을 바이너리 baz로 링크해라."
그는 명령형 빌드 스크립트가 현실의 근본적인 구조(underlying structure of reality)를 모델링하는 데 실패하기 때문에 취약하다는 것을 깨달았습니다:
- 타겟 (Targets): 우리가 생산하려고 하는 최종 상태 아티팩트 또는 검증된 조건은 무엇인가?
- 전제 조건 (Prerequisites): 이 타겟을 빌드할 수 있도록 허용되기 전에, 어떤 상위(upstream) 아티팩트가 존재해야 하며—타겟보다 최신이어야 하는가?
- 레시피 (Recipes): 전제 조건으로부터 타겟을 생성하는 물리적인 명령어 또는 행동은 무엇인가?
make는 단계 번호에 신경 쓰지 않습니다. 그것이 신경 쓰는 것은 종속성의 **방향성 비순환 그래프(Directed Acyclic Graph, DAG)**입니다.
핵심 돌파구 (The Core Breakthrough)
자율 AI 코딩 에이전트의 워크플로우는 절차적 스크립트가 아닙니다. 그것은 물리적인 소프트웨어 아티팩트와 검증된 불변성(verified invariants)으로 구성된 방향성 비순환 그래프(Directed Acyclic Graph, DAG)입니다.
flowchart TD
T1["1. ticket-assigned"] --> T2["2. approved-plan\n(Human Plan Airlock)"]
T2 --> T3["3. implementation-diff\n(Red-Green TDD)"]
...
3. 표준 에이전트 Makefile: 이슈에서 배포된 PR까지
20개의 취약한 번호 매긴 단계 대신, 소프트웨어 엔지니어링의 전체 수명 주기는 에이전트의 스킬 정의 내에 선언적(declarative)인 Makefile DAG로 표현될 수 있습니다. 여기서 모든 인간 검토 지점과 품질 기준은 경계가 있는 전제 조건(bounded prerequisites)을 가진 개별적인 타겟입니다:
.PHONY: finish land ready-to-land ci-quiescent push commit pre-commit-clean \
approved-adversarial-report adversarial-review implementation-diff \
approved-plan researched-ticket ticket-assigned review-ready ship fast-track
...
새로운 티켓에 에이전트를 배포할 때, 최상위 목표는 항상 동일합니다:
make finish
finish에서 가장 깊은 만족되지 않은 리프 노드(leaf)까지 그래프를 역방향으로 평가하면 정확한 실행 궤적을 즉시 유도합니다:
ticket-assigned → researched-ticket → approved-plan → implementation-diff → ... → finish
4. 경계가 있는 Fan-In 불변성: 왜 긴 전제 조건 목록이 LLM에서 실패하는가 (Feldman 삼각 법칙)
왜 모든 전제 조건을 이처럼 단일 타겟 라인에 붙일 수 없을까요?
# ❌ 전제 조건 희석 함정 (한 줄에 5개 전제 조건)
land: push ci-remote-green all-bots-triaged changelog-updated human-landing-approval
gh pr merge --squash
고전적인 GNU Make에서, 열 개의 전제 조건을 가진 타겟은 C 프로그램이 하드 CPU 루프 카운터를 사용하기 때문에 왼쪽에서 오른쪽으로 결정론적으로 실행됩니다.
LLM은 C 프로그램이 아닙니다. 그것은 자체 주의 가중치(self-attention weights)와 예측적 모멘텀에 의해 지배되는 자기회귀 변환기(autoregressive transformer)입니다.
143개의 실제 운영 티켓에 대한 경험적 필드 테스트를 거치면서, 우리는 보편적인 인지 위험 요소인 전제 조건 희석 함정(The Prerequisite Dilution Trap)(SCAR-PROC-91)을 발견했습니다:
- 주의 가중치 감쇠 (Attentional Weight Attenuation): 전제 목록이 3개 항목을 초과하여 늘어날 경우, 목록의 후반부 토큰에 할당되는 자체 주의(self-attention)가 급격히 감소합니다.
- 자기회귀 검증 모멘텀 (Autoregressive Verification Momentum): 에이전트가 네 개의 연속적인 기계적 전제 조건(
push→ci-remote-green→all-bots-triaged→changelog-updated)을 성공적으로 검증하면, 멈추지 않고 계속 진행할 조건부 확률이1.0에 가까워집니다. 다섯 번째 항목(human-landing-approval)은 더 이상 움직일 수 없는 장벽이라기보다는 수사적인 체크박스로 취급되어, 모델이 인간의 승인을 구하지 않고 PR을 일방적으로 병합하도록 유혹합니다. - 작업 기억 청킹 한계 (Working Memory Chunking Limits): 조지 밀러(George Miller)의 고전적인 인지 용량 한계(
7 ± 2청크, 이는 밀집된 도구 호출 컨텍스트에서3 ± 1로 압축됨)에 근거하여, 에이전트는 네 개의 저장소 상태를 동시에 검증하면서도 하드 스톱 조건에 대한 감시 주의(sentinel attention)를 유지할 수 없습니다. - 누락된 상태 레지스터 (The Missing State Register): 명령어 포인터(
int index = 3;)가 있는 CPU와 달리, 트랜스포머는 내부 정수 레지스터가 없습니다. 이는 쌍별 이진 종속성(A가B보다 먼저)을 거의 100%의 신뢰도로 해결하지만, 터미널 로그가 컨텍스트 창을 채우면서 5개 항목 목록 내에서의 순서적 위치 추적이 위치적 흐릿함(positional blur)으로 저하됩니다.
펠드먼 삼요소 불변성 (The Feldman Triad Invariant): 대상당 최대 2~3개의 전제 조건
전제 조건 희석을 제거하기 위해, 에이전트 워크플로우의 모든 Makefile 타겟은 **유한 팬-인 불변성(Bounded Fan-In Invariant)**을 준수해야 합니다:
1 <= |Prerequisites(Target)| <= 3
모든 특권 사용자 검토 지점(approved-plan, commit, push, land)은 엄격하게 두 개의 전제 조건—복합적인 준비 상태 타겟과 명시적인 인간 승인 게이트—을 가진 환원 불가능한 **원자적 장벽 튜플(Atomic Barrier Tuple)**로 구성됩니다:
action-target: ready-state human-approval
flowchart TD
P1["ci-quiescent\n(Green 체크 + 봇 트리아지 완료)"] --> R["ready-to-land\n(1. 기계적 준비 목표)"]
P2["changelog-updated\n(CHANGELOG.md 검증됨)"] --> R
...
이러한 두 가지 전제 조건 토폴로지 하에서, 에이전트가 에어록에서 내리는 결정은 엄격하게 이진적입니다:
ready-to-land가 물리적으로 충족되었는가? 예.- 현재 사용자 턴에서
human-landing-approval이 부여되었는가? 아니요. - 결과 → 중지 (STOP) (
tool_calls: []). 상태를 제시하고 인간의 응답을 기다립니다.
광범위한 전제 조건 목록을 얕은 2~3개 항목의 하위 목표로 분해함으로써, 인간 승인 게이트는 돌파할 수 없는 다익스트라(Dijkstra) 장벽이 됩니다.
5. 명령형 루프를 선언적 고정점(Fixed Points)으로 대체하기
Makefile DAG가 프롬프트에서 모든 while 루프, 재시도 카운터, 조건부 GOTO를 어떻게 제거하는지 확인해 보세요:
Satisfied(target) ⇔ (∀ p ∈ Prerequisites: Satisfied(p)) ∧ Invariant(target) == true
-
무효화 시 자체 복구: 만약 당신이
ci-quiescent상태에 있고, 자동 검토 봇이 GitHub에 합법적인 버그를 발견하여 게시했다고 가정해 봅시다. 당신은 _ -
인지 부하가 O(1)로 감소합니다: 에이전트는 더 이상 "_제가 초기 구현의 4단계에 있는지, 아니면 두 번째 봇 복구 사이클의 4단계에 있는지?"와 같은 질문을 할 필요가 없습니다. 오직 하나의 질문만 합니다: "지금 제가 구축하고 있는 단일 리프 타겟은 무엇이며, 그 물리적 불변성(physical invariant)이 유지되고 있습니까?"
6. 세션 경계 해상도 오라클 (The Session Frontier Resolution Oracle): 어디서든 O(1)로 재개하기
Makefile 기반 에이전트는 사용자가 진행 중인 브랜치 중간이나 휴식 후에 어디서부터 작업을 시작해야 할지 어떻게 알까요?
에이전트는 대화형 메모리에 의존하는 대신, **세션 경계 해상도 오라클(Session Frontier Resolution Oracle)**을 실행합니다. 이는 리포지토리와 GitHub forge의 물리적 상태를 검사하여 make finish의 가장 깊은 미충족 전제 조건(prerequisite)을 찾아냅니다:
| 물리적 Git / Forge 상태 | 해결된 활성 타겟 (Resolved Active Target) | 자연어 운영자 프롬프트 (Natural Operator Prompt) |
|---|---|---|
| 주석이 처리되지 않았거나 빨간 CI가 있는 PR 열림 상태 | ci-quiescent | "봇 리뷰를 분류하세요" |
| ... |
에이전트에게 현재 몇 단계에 있는지 알려줄 필요가 없습니다. 파일 시스템과 git 그래프 자체가 상태 머신(state machine)입니다.
7. 보정된 속도 (Calibrated Velocity): 일일 엔지니어링을 위한 메타 타겟
모든 작업이 완전한 제로에서 병합까지의 자율 실행을 필요로 하는 것은 아닙니다. 실제 Makefile처럼, 저희 워크플로우는 인체공학적인 메타 타겟(meta-targets)을 노출합니다:
make finish(전체 수명 주기): 이슈 선택(ticket-assigned)부터 PR 병합(land), 그리고 사후 분석 흉터 추출(codified-scars-consolidated)까지 모든 과정을 포괄합니다.make review-ready: 이슈 조사부터 TDD(Test-Driven Development), 적대적 자체 검토, 커밋, 그리고 PR 열기까지 실행한 후 중단하여 인간 팀이 여유롭게 검토할 수 있도록 합니다.make ship: 편집기에서 코드를 상호작용적으로 작성하거나 수정하고
AI 자동 생성 콘텐츠
본 콘텐츠는 Dev.to AI tag의 원문을 AI가 자동으로 요약·번역·분석한 것입니다. 원 저작권은 원저작자에게 있으며, 정확한 내용은 반드시 원문을 확인해 주세요.
원문 바로가기