명세(Spec)가 잘못된 위치에 있습니다
요약
코딩 에이전트의 성능을 높이기 위해서는 프롬프트보다 명세(Spec) 기반 개발이 중요하지만, 현재 명세가 의사결정 시점과 동떨어진 엔지니어의 작업 단계에서 작성되는 문제를 지적합니다. 진정한 품질을 위해서는 프로젝트 시작 단계부터 팀 전체가 참여하여 명세를 정의해야 합니다.
핵심 포인트
- 명세 기반 개발(Spec-driven development)이 에이전트 결과물의 품질을 결정함
- 현재 명세는 실제 의사결정 시점과 괴리된 채 엔지니어에 의해 사후 재구성됨
- 에이전트의 빠른 실행 속도로 인해 모호한 명세는 잘못된 결과물을 즉각 양산함
- 명세는 키보드 앞의 즉석 산출물이 아닌, 프로젝트 시작 시점의 합의된 지점이 되어야 함
제 본업은 대형 기술 기업에서 일하는 것입니다. 수백 개의 엔지니어링 팀이 있으며, 그들 모두는 AI 도입 단계에서 각기 다른 위치에 있습니다. 어떤 팀은 여전히 코딩 에이전트(coding agents)를 단순한 호기심 대상으로 취급합니다. 어떤 팀은 조용히 에이전트를 중심으로 전체 워크플로우(workflow)를 재구축했습니다. 대부분은 혼란스러운 중간 단계에 머물러 있으며, 그 중간 과정을 지켜보는 과정에서 Penling에 대한 아이디어가 떠올랐습니다.
명세 기반 개발(Spec-driven development)이 도래했으며, 저는 이것이 올바른 방향이라고 생각합니다. SpecKit이나 Kiro와 같은 도구들은 명세(specification)를 코딩 워크플로우의 중심에 두며, 그 결과는 눈에 띄게 더 좋습니다. 즉, 느낌(vibe)이나 프롬프트(prompt)에 의존하는 에이전트보다 작성된 명세에 따라 작동하는 에이전트가 훨씬 더 나은 결과물을 만들어냅니다.
하지만 명세가 작성되는 _위치_를 보십시오. 엔지니어의 IDE에서, 터미널에서, 그리고 작업이 할당되는 바로 그 순간에 작성됩니다.
이는 제품 결정이 실제로 내려진 곳과는 거리가 매우 멉니다.
하나의 의도(intent)가 터미널에 도달하기까지 거치는 여정을 생각해 보십시오. 팀은 기획 세션에서, 전략 문서에서, 혹은 회의가 되었어야 할 스쳐 지나가는 대화 속에서 무언가를 결정합니다. 그 결정은 티켓(ticket)으로 압축됩니다. 아마 그 티켓은 몇 주 동안 백로그(backlog)에 머물러 있을지도 모릅니다. 결국 엔지니어가 이를 가져와 제공된 컨텍스트(context)를 읽고, 에이전트를 위한 명세를 작성합니다.
제 경험상, 티켓이 작성되는 방식을 고려할 때 그 명세는 아마도 팀의 온전한 의도를 담고 있지 않을 것입니다. 그것은 실제 결정이 내려진 지 몇 주가 지난 후, 마감 기한에 쫓기며 작성된, 팀의 의도가 무엇이었을지에 대한 엔지니어의 재구성일 뿐입니다. 번역의 번역인 셈입니다. 그러고 나서 우리는 그것을 에이전트에게 전달하고, 에이전트가 명세에 적힌 그대로 빠르고 자신 있게 구축하도록 내버려 둡니다.
에이전트들은 자신의 일을 잘 수행하고 있습니다. 다만 명세가 잘못된 위치에 있을 뿐입니다.
저는 AI 코딩 도구가 존재하기 훨씬 전부터 오랫동안 이것을 믿어왔습니다. 즉, 작업의 품질은 작업이 시작되기 전에 대부분 결정된다는 사실입니다. 팀들은 목적과 범위(scope)에 대해 합의하기도 전에 일관되게 실행에 착수하며, 나중에 발생하는 거의 모든 고통스러운 일들 — 재작업(rework), 표류(drift), 아무도 요청하지 않은 기능 — 은 모두 그 지점으로 거슬러 올라갑니다.
코딩 에이전트(Coding agents)가 이 문제를 만든 것은 아닙니다. 그들은 이 문제를 시급하게 만들었을 뿐입니다. 과거에는 실행 비용이 충분히 높았기에 불일치(misalignment)가 천천히 드러났습니다. 개발 2주 차쯤 되면 오해를 발견할 수 있었죠. 하지만 이제 실행은 거의 비용이 들지 않으며 거의 즉각적입니다. 에이전트는 브리프(brief)가 모호했다는 것을 누군가 알아차리기도 전에, 완전히 잘못된 것을 아주 아름답게 만들어버릴 것입니다.
따라서 "우리는 그것을 만들 수 있다"와 "우리는 그것이 무엇이어야 하는지에 대해 합의했다" 사이의 간극은 이제 소프트웨어 프로젝트에서 리스크의 대부분을 차지합니다. 어쩌면 리스크의 전부일지도 모릅니다.
이는 명세(spec) — 우리가 무엇을 만들고 성공이 어떤 모습인지에 대해 작성되고 합의된 진술 — 가 키보드 앞에서 즉석(just-in-time)으로 만들어지는 산출물이어야 해서는 안 된다는 것을 의미합니다. 그것은 프로젝트가 시작되는 지점이어야 합니다. 제품(product), 엔지니어링(engineering), 결과에 책임을 지는 누구든 상관없이 이를 만드는 데 참여하는 팀 전체가 함께해야 합니다. 논쟁하는 과정에서 논쟁하는 것은 여전히 비용이 적게 듭니다. 무엇인가가 구축되기 전에 '완료(done)'가 무엇을 의미하는지에 대해 합의하십시오.
그렇게 하면 두 가지 일이 동시에 일어납니다. 프로젝트의 성공을 실제로 결정되는 시점인 시작 단계에서 결정하게 됩니다. 그리고 에이전트를 팀이 설정한 경계 내로 제한하게 됩니다. 어느 시점에 전달받은 내용으로부터 한 엔지니어가 추론한 경계가 아니라 말입니다.
당연한 반론이 있을 수 있습니다: 이미 이를 위한 도구들이 있지 않나요? 우리는 프로젝트 트래커(project trackers)를 가지고 있습니다. 위키(wikis)도 있습니다. 명세 기반 개발 도구(spec-driven dev tools)도 있습니다. Jira, Confluence, SpecKit 사이에서 이 문제는 분명히 해결되었을 것입니다.
저는 그렇지 않다고 생각하며, 그 이유는 각각의 도구가 올바른 것을 잘못된 위치에 담고 있기 때문입니다.
Confluence는 팀의 의도(intent)를 담고 있지만, 코드와는 멀리 떨어져 있습니다. 문서와 실제로 구축되는 것 사이를 연결해 주는 것이 아무것도 없습니다. 코드와 함께 버전 관리(versioning)가 되지 않으며, 에이전트(agent)는 이를 읽지 못하고, 작성된 다음 날부터 바로 부패하기 시작합니다. 모두가 설계 문서(design doc)를 열어보고는, 이것이 현재의 시스템을 설명하고 있는지 아니면 거의 만들어질 뻔했던 시스템을 설명하고 있는지 의구심을 품어본 적이 있을 것입니다.
Jira는 작업 분할(breakdown) 내용을 담고 있지만, 티켓(ticket)은 추론 과정이 제거된 채 의도만을 담고 있습니다. 티켓은 이번 스프린트(sprint)에서 _무엇(what)_을 해야 하는지는 알려주지만, 왜(why) 해야 하는지, 혹은 성공적인 결과물이 어떤 모습이어야 하는지에 대해서는 아무것도 알려주지 않습니다.
SpecKit은 올바른 산출물(artefact) — 즉, 코드 옆에 위치하며 에이전트가 읽을 수 있는 실제 명세(spec) — 을 보유하고 있습니다. 하지만 이는 구현(implementation) 시점에 엔지니어와 함께 존재하며, 이것이 바로 문제입니다. 이는 터미널 세션(terminal session) 범위 내로 한정된 명세 주도 개발(spec-driven development)에 불과합니다. 명세가 기록해야 할 결정들은 몇 주 전에, 한 명보다 더 많은 사람에 의해 이미 내려졌기 때문입니다.
의도는 세 곳 모두에 부분적으로 존재하지만, 그 어디에도 지속 가능하게(durably) 존재하지 않습니다. 그리고 이 모든 것의 밑바닥에는 더 조용한 문제가 있습니다. 현재 명세가 위치한 곳 — 리포지토리(repo) — 에 팀원 대부분이 접근조차 할 수 없다는 점입니다. 만약 당신의 회사가 우리 회사와 비슷하다면, 제품 관리자(product manager)들은 GitHub 라이선스를 가지고 있지 않을 것입니다. 따라서 실제 명세가 존재하더라도, 그 명세에 대해 의견을 내야 할 사람들은 결코 그것을 보지 못합니다.
배치(placement) 문제를 진지하게 받아들인다면, 제품 설계(product design)의 대부분이 이 문제에서 탈락하게 됩니다.
명세는 지속 가능해야 하므로, 설명하고자 하는 코드와 함께 버전 관리되어 리포지토리에 커밋된 마크다운(markdown) 파일로 존재해야 합니다. 하지만 팀 전체가 접근할 수 있는 곳 — 즉, 팀의 절반이 라이선스를 가지고 있지 않은 장벽 뒤가 아니라, 공유된 환경에서 누구나 읽을 수 있는 형식 — 에서 작성되어야 합니다.
또한 명세가 우선되어야 하므로, 워크플로(workflow)는 백로그(backlog)가 아닌 브리프(brief)에서 시작되어야 합니다. 대략적인 아이디어가 팀에 의해 명세로 구체화되고, 명세는 실행 가능한 작업으로 분할되며, 에이전트는 그 명세를 바탕으로 구축합니다. 계획(planning), 분할(breakdown), 구축(build)은 모두 하나의 산출물(artefact)에 매달려 있습니다. 왜냐하면 이 워크플로에서 이들은 애초에 결코 별개의 것이 아니었기 때문입니다.
그것이 전부입니다. 나머지는 세부 사항일 뿐입니다.
바이브 코딩 (Vibe-coding)으로 프로토타입을 만드는 것은 진정으로 멋진 일입니다. 명세 (spec)가 필요 없으며, 그렇지 않다고 말하는 사람은 프로세스를 팔고 있는 것입니다. 하지만 그 프로토타입에 사용자, 팀, 로드맵이 생기는 순간 — 즉, 그것을 만든 사람이 떠난 후에도 계속해서 올바른 일을 수행해야 하는 순간 — 누군가는 그것이 무엇을 해야 하는지를 기록해야 합니다. 어딘가 내구성이 있는 곳에 말이죠. 다음 사람, 그리고 다음 에이전트 (agent)가 실제로 찾아볼 수 있는 곳에 말입니다.
만약 당신의 팀이 오늘날 에이전트 (agents)를 활용해 구축하고 있다면, 당신의 명세 (spec)가 어디에 작성되는지, 그리고 누가 작성하는지 — 혹은 작성되기는 하는지 — 를 알아둘 가치가 있습니다.
Paul은 시드니의 소프트웨어 엔지니어이자, LLM을 활용해 구축하는 팀들을 위한 명세 기반 전달 (spec-driven delivery) 플랫폼인 Penling의 창립자입니다.
AI 자동 생성 콘텐츠
본 콘텐츠는 Dev.to AI tag의 원문을 AI가 자동으로 요약·번역·분석한 것입니다. 원 저작권은 원저작자에게 있으며, 정확한 내용은 반드시 원문을 확인해 주세요.
원문 바로가기