가치 사슬의 역전
최근 흥미로운 표현을 접했습니다. "가치 사슬의 역전." 처음에는 거창한 경영학 용어처럼 들렸지만, 곱씹어 보니 요즘 코드를 대하는 방식이 정확히 이 단어로 설명됩니다.
원래 우리가 알던 순서
개발자가 코드를 작성하는 흐름은 늘 비슷했습니다. 기능을 구현하고, 잘 돌아가는지 확인하고, 그다음에 시간이 남으면 테스트를 붙입니다. 현실적으로 테스트는 늘 후순위였습니다. 기능 구현이 "진짜 일"이고, 테스트는 그걸 보조하는 안전망 정도의 위치. 테스트 코드를 작성하는 것이 중요하다는 건 머리로는 알지만, 당장 눈앞의 기능 구현 앞에서 늘 밀려나는 존재였습니다.
구현 → 테스트. 이 순서가 너무 당연해보여서, 누구도 의심하지 않았습니다.
전제가 바뀌었습니다
LLM이 코드를 쓰기 시작했습니다. 처음에는 자동완성 수준이었고, 조금 지나니 함수 하나를 통째로 만들어줬습니다. 그리고 어느 순간 Tab만 누르던 시기를 지나, 지금에 이르러서는 Agent가 task를 받아서 여러 파일에 걸쳐 코드를 생성하고, 스스로 실행해보고, 수정까지 합니다.
생산성이 작게는 몇 배, 크게는 수십 배 늘었다는 이야기가 여기저기서 나옵니다. Google은 내부 AI Agent가 production 코드의 30% 이상을 생성한다고 밝혔고, 어떤 팀은 80% 인원으로 170%의 처리량을 달성했다고 합니다. 숫자가 과장이든 아니든, 한 가지는 분명합니다. 코드를 "만들어내는 것" 자체는 더 이상 병목이 아닙니다.
하루에도 수천 줄을 만들어낼 수 있는 시대가 왔습니다. 그러면 자연스럽게 질문이 따라옵니다. 그 수천 줄이 적절한 코드인가, 기존 기능을 해치지는 않는가, 그리고 인간의 역할은 무엇인가.
역전이 일어나는 지점
여기서 가치 사슬이 뒤집힙니다.
예전에는 구현 코드가 "본체" 였고, 테스트 코드는 그 본체가 잘 동작하는지 확인하는 "보조" 였습니다. 하지만 AI가 구현을 담당하게 되고, 그 구현이 쉬워짐에 따라 진짜 가치 있는 작업은 "무엇이 올바른 동작인지 정의하는 것" 으로 옮겨갑니다. 그리고 그 정의가 코드로 표현된 형태가 바로 테스트입니다.
다시 말해서, 테스트 코드가 본체가 되고, 구현 코드가 그 테스트를 통과하기 위해 존재하는 보조가 됩니다.
이것이 TDD(Test-Driven Development)의 부활처럼 보일 수 있지만, 결이 다릅니다. TDD는 "테스트를 먼저 작성하면 설계가 좋아진다"는 개발 방법론이었습니다. 지금 일어나고 있는 것은 방법론의 문제가 아니라, 가치의 무게 중심 자체가 이동한 것 입니다. AI가 구현을 대체할수록 인간이 작성한 테스트의 가치는 올라갑니다. 구현은 언제든 다시 생성할 수 있지만, "이 시스템이 어때야 하는가"라는 판단은 대체할 수 없기 때문입니다.
리팩토링에서 더 극명해집니다
이 역전이 가장 체감되는 순간은 리팩토링입니다.
기존에 잘 돌아가던 코드를 구조적으로 개선하고 싶다고 해보겠습니다. Agent에게 "이 모듈을 리팩토링해줘"라고 요청하면, Agent는 기꺼이 코드를 갈아엎습니다. 순식간에 처리하고, 꽤 그럴듯합니다. 문제는 그 결과물이 기존에 보장하던 동작을 여전히 보장하는지 확인할 방법이 필요하다는 것입니다.
테스트가 없으면 리팩토링의 결과를 검증할 방법이 사라집니다. Agent가 아무리 빠르게 코드를 바꿔줘도, 바뀐 코드가 맞는지 틀린지 알 수 없습니다. 결국 사람이 눈으로 전부 확인해야 하고, 그 순간 AI가 가져다준 생산성 향상은 증발합니다.
반대로 테스트가 탄탄하면, Agent에게 자유롭게 리팩토링을 시키고, 테스트를 돌리고, 통과하면 merge합니다. 테스트가 곧 신뢰의 기반 이 됩니다. 코드의 품질을 보장하는 것은 구현의 정교함이 아니라 테스트의 포괄성입니다.
코드에서 의도로
이제 개발자에게 더 중요한 역량은 "코드를 빠르게 작성하는 능력"이 아니라, "올바른 동작을 정확하게 정의하는 능력" 입니다.
이 역전이 테스트에서만 일어나는 것은 아닙니다. 최근 들리는 방법론 중 하나는, Agent가 수천 줄의 코드를 생성한 경우 그 코드 자체를 한 줄 한 줄 review하는 대신 "어떤 prompt를 통해 이 코드를 만들게 됐는지" 그 의사결정 문서를 공유하는 것으로 code review를 대체한다 는 것입니다. 같은 맥락입니다. 수천 줄의 구현 코드를 사람이 읽는 것은 이미 비효율적이고, 진짜 review해야 할 대상은 "왜 이렇게 만들었는가"라는 의도와 판단, 즉 코드의 상류에 있는 것들입니다.
테스트 코드가 "이 시스템이 어때야 하는가"를 정의하는 것이라면, prompt 문서는 "왜 이런 방향으로 만들었는가"를 정의하는 것입니다. 둘 다 구현 코드보다 상위에 있는 판단이고, 둘 다 사람의 머리에서 나옵니다. 가치 사슬의 역전은 결국, 코드에서 의도로 무게 중심이 옮겨가는 흐름의 다른 이름입니다.
좋은 테스트를 작성한다는 것은 시스템이 어떻게 동작해야 하는지를 명확하게 이해하고 있다는 뜻입니다. 어떤 입력에 어떤 출력이 나와야 하는지, 어떤 경계 조건에서 어떤 에러가 발생해야 하는지, 사용자가 예상치 못한 행동을 했을 때 시스템이 어떻게 반응해야 하는지. 이런 판단은 도메인에 대한 깊은 이해에서 나옵니다. 그리고 이것은 아직, 그리고 앞으로도 한동안, 사람의 영역입니다.
가치 사슬이 역전된 세상에서 테스트 코드는 더 이상 안전망이 아니라 설계도 에 가깝습니다. AI가 만들어내는 수천 줄의 코드가 어디로 향해야 하는지 방향을 잡아줍니다. 그 설계도의 품질이 곧 시스템의 품질을 결정합니다. 다음 글에서는 그 설계도를 잘 그리는 법, 즉 좋은 테스트와 나쁜 테스트의 차이를 구체적인 코드와 함께 살펴보겠습니다.
kyu-log