아이디어 사이클 회고 #5 — 다시 만든다면 이렇게 했다
결론부터
다시 만든다면 순서를 바꾼다. 단일 진실원 프롬프트(scripts/cycle-prompt.md) → 디자인 토큰(public/tokens.css) + 린트(npm run lint:design) → Stage 5 QA(Playwright MCP) → Picker 5축 → Stage 0 메모리 순으로 깐다. 처음엔 Implementer부터 만들었는데 — 거꾸로였다. 가드레일이 깔리기 전의 Implementer는 매일 다른 걸 만들고, 다른 걸 부순다.
세 가지 후회와 세 가지 유지하고 싶은 결정이 있다.
후회 — 이걸 더 빨리 했어야 했다
1. 토큰을 1편부터 강제했어야 한다. 초기 사이클 몇 편은 hex literal이 그냥 들어가 있었고, 나중에 lint:design을 켰을 때 줄줄이 위반이 떴다. 토큰 파일이 110줄짜리라서 만드는 건 한 시간이면 충분했는데, 그걸 미루는 동안 결과물의 시각적 일관성이 매일 흔들렸다. 가드레일은 먼저 깔아야 한다.
2. Stage 5(QA)를 더 일찍 박았어야 한다. Playwright MCP를 붙이기 전 며칠 동안, 콘솔 에러가 있는 사이클이 그대로 라이브에 올라가는 걸 사후에 발견했다. 자동화는 abort 경로가 없으면 결국 망가진 결과물이 누적된다. 검증 없는 자동화는 노이즈 생성기다.
3. recent_critiques 메모리는 처음부터 들어갔어야 한다. Stage 0가 없을 때, Reviewer가 매일 비슷한 약점을 반복해서 지적했다. "모바일이 얕다", "두 번째 레벨이 단조롭다" — 다음날 Picker는 그 정보를 못 받으니 같은 함정을 또 골랐다. 비판을 픽 단계에 forward만 해도 같은 실수가 줄어든다.
세 후회 모두 공통점이 있다 —
. Implementer를 먼저 잘 만들고 싶은 충동이 강했지만, 매일 굴리는 파이프라인은 한 편의 품질이 아니라 30편의 누적 품질로 평가된다. 누적 품질을 결정하는 건 메타 레이어다.
유지하고 싶은 결정
1. 코드보다 프롬프트가 단일 진실원 (scripts/cycle-prompt.md)
2. 자연어 사양 + 강제 JSON 출력의 하이브리드 (json scout / ideas / picker)
3. 6단계 파이프라인 — Scout / Ideator / Picker / Implementer / QA / Reviewer1. 코드 대신 프롬프트가 단일 진실원이다. 6단계의 행동 규칙은 전부 한 마크다운 파일에 있다. PS 래퍼와 디자인 린트만 코드로 남기고, 분기·판단·평가가 많은 부분은 자연어로 둔다. 코드로 옮기고 싶을 때마다 참았던 게 결과적으로 옳았다 — LLM 파이프라인은 자연어 사양에서 훨씬 안정적이다.
2. 자연어 사양 + 강제 JSON 출력의 하이브리드. Stage 1·2·3은 free-form 분석을 하면서도 마지막에 fenced JSON 블록을 강제로 emit한다. 다음 단계는 그 JSON을 읽는다. "structured output for handoff, prose for reasoning." 둘 다 필요했다.
3. 6단계 분리. 한 LLM 세션 안에서 Scout부터 Reviewer까지 다 돈다. 분리해서 다른 모델·다른 컨텍스트로 굴리는 것도 시도했지만, 컨텍스트 유실이 더 컸다. 같은 세션에서 역할만 명시적으로 바뀌는 지금 구조가 가장 단순하고 안정적이다.
결국 시리즈 전체의 한 줄 —
한 편씩이 아니라 누적이다.
시리즈를 닫으며
idea-cycles는 지금도 매일 새벽 5시에 한 편씩 굴러가고 있다. 라이브: https://idea-cycles.vercel.app. 시리즈 1편에서 약속한 "왜 만들었나"부터 5편의 "다시 만든다면"까지 — 매일 자동화에 가드레일을 깔고, 실패를 침묵하지 않게 만들고, 픽 단계에 메모리를 박아주는 구체적인 방법들을 한 번씩 짚었다. 같은 모양의 자동화 파이프라인을 만들고 있는 누군가에게 한 줄이라도 도움이 됐기를 바란다.
읽어주셔서 감사합니다.