코드 리뷰의 목적은 버그를 잡는 데 있지 않으며, 프로세스 실패를 드러내고 팀 문화를 형성·갱신하는 사회적 활동이라는 점을 설명한다.
코드 리뷰는 버그를 잡기 위한 것이 아니다.
programmingprocessaillmTuesday March 03, 2026
인간은 버그를 찾아내는 데 그다지 능숙하지 않다. 한 가지로, 우리는 쉽게 피로해진다. 이에 관한 과학적 근거도 있는데, 인간은 한 번에 약 400줄 이상의 코드를 리뷰할 만큼 충분한 집중력을 유지하지 못한다는 것을 시사한다..
우리는 다양한 분야에서, 인간의 지각 시스템이 자극을 등록하지 못하는 방식에 대해 이미 확립된 전문 용어들을 가지고 있다. 인간이 주의가 분산되거나, 피곤하거나, 과부하되었거나, 혹은 그저 부적절하게 관여하고 있을 때 지각은 실패한다.
이 각각은 엔지니어링 실천으로서 코드 리뷰의 근본적 한계에 대한 함의를 갖는다:
부주의 맹시(Inattentional Blindness): 찾고 있지 않은 버그는 신뢰할 만하게 찾아낼 수 없다.
반복 맹시(Repetition Blindness): 버그가 계속 반복된다면, 찾고 있는 버그조차도 신뢰할 만하게 찾아낼 수 없다.
경계 피로(Vigilance Fatigue): 항상 버그의 존재에 경계해야 한다면, 두 종류의 버그 모두를 신뢰할 만하게 찾아낼 수 없다.
그리고 물론, 별개이지만 관련된 경보 피로(Alert Fatigue): 오탐이 너무 많다면, 가능한 버그에 대한 보고를 신뢰할 만하게 평가조차 할 수 없다.
코드에서 어떤 오류 범주를 신뢰성 있게 잡아내야 한다면, 결정론적 도구가 평가하도록 해야 한다 — 그리고 위에서 언급한 우리의 오랜 친구 “경보 피로” 덕분에, 이상적으로는 그런 오류를 수정까지 하도록 해야 한다. 이런 도구들은 사람이 같은 반복적 점검을 계속 되풀이해야 하는 필요를 덜어줄 것이다. 어느 것도 완벽하진 않지만:
리뷰어가 이런 것들을 놓쳤다고 탓하지 마라.
코드 리뷰는 버그를 잡는 방식이어서는 안 된다.
코드 리뷰는 세 가지를 위한 것이다.
첫째, 코드 리뷰는 프로세스 실패를 잡기 위한 것이다. 리뷰어가 코드 리뷰에서 같은 유형의 버그를 몇 번이나 알아챘다면, 그 버그 유형은 잡히는 것보다 리뷰를 통과하는 경우가 더 많다는 신호다. 이는 CI에 도구나 테스트를 배치해 그 오류 범주를 더 이상 리뷰어가 경계하지 않아도 신뢰성 있게 방지할 방법을 찾아야 할 때라는 뜻이다.
둘째 — 그리고 이것이 사실 더 중요한 목적이다 — 코드 리뷰는 문화적 적응(Acculturation)을 위한 도구다. 좋은 도구, 좋은 프로세스, 좋은 문서가 이미 있더라도, 팀의 새 구성원은 그런 것들을 반드시 알고 있지는 않다. 코드 리뷰는 오래된 팀 구성원이 새 구성원에게 기존 도구, 패턴, 혹은 책임 영역을 소개할 기회다. 예를 들어 observer pattern을 구현하고 있다면, 작업 중인 코드베이스에 이미 그 일을 하기 위한 기존 관용구가 있다는 것을 깨닫지 못해 아예 검색조차 생각하지 못할 수 있다. 하지만 코드에 더 익숙한 다른 사람은 그것을 알고 있어 중복을 피하도록 도울 수 있다.
내가 그 문단에서 “junior”나 “senior”라는 표현을 조심스럽게 피했다는 것을 알아차렸을 것이다. 때로는 새 팀 구성원이 실제로 더 시니어이기도 하다. 하지만 문화적 적응은 한 방향만이 아니다. 이것이 코드 리뷰의 셋째 목적이다: 팀 문화에 교란을 주어 정체를 피하는 것. 새로운 재능이 들어오면, 신선한 관점 또한 건강한 문화를 만드는 데 매우 가치 있는 도구가 될 수 있다. 팀에 새로 들어와 observer pattern으로 무언가를 만들려는데 이 코드베이스에는 그를 위한 도구가 없고, 하지만 이전 직장에서는 오픈 소스 라이브러리의 도구를 사용했다면, 그 또한 리뷰에서 지적하기에 좋은 내용이다. 이는 프로세스의 개선 지점을 찾는 것만큼이나, 문화의 개선 지점을 찾는 기회다.
그러므로 코드 리뷰는 가능한 한 계층적으로 평평해야 한다. 코드 리뷰의 목표가 버그를 찾아내는 것이라면, 조직에서 가장 시니어하고 세부에 집착하며 엄격한 엔지니어에게만 코드 리뷰 권한을 제한하는 것이 타당해 보일 것이다. 하지만 대부분의 팀은 이미 그게 취약성, 정체, 병목으로 이어지는 처방이라는 것을 알고 있다. 따라서 팀원 모두가 버그를 똑같이 잘 찾아내지는 못한다는 것을 알고 있음에도, 대부분의 팀에서는 꽤 낮은 최소 숙련도 기준만 넘으면 누구나 리뷰를 하도록 허용하는 경우가 흔하다. 종종 그 기준은 “온보딩을 끝낸 팀원 전원” 수준까지 내려간다.
한숨. 나도 여러분만큼 실망스럽지만, 달리 말할 길이 없다: LLM 코드 생성기는 이제 어디에나 있고, 우리는 그것들을 어떻게 다룰지 이야기해야 한다. 그러므로 코드 리뷰가 사회적 활동이라는 이 이해에서 중요한 귀결은, LLM은 사회적 행위자가 아니므로 코드 리뷰에 그 출력물을 검사하도록 기대할 수 없다는 점이다.
내 개인적 선호는 그 사용을 아예 피하는 쪽이겠지만, 피해 최소화의 정신으로, LLM을 사용해 코드를 생성할 거라면 LLM이 인간과 어떻게 다른지 기억해야 한다.
인간 동료와 관계를 맺을 때는 다음을 기대하게 된다:
반면 LLM에서는, 엔지니어의 프롬프트와 저장소에 존재할지 모르는 사전 프롬프트에 의해 오류가 어느 정도 편향될 수는 있지만, LLM이 만드는 오류 유형은 경험 범위 전반에 걸쳐 보다 균일하게 분포하는 경향이 있다.
여전히 supposedly 매우 정교한 LLM들이 극히 흔한 실수를 저지르는 것을 보게 될 것이다. 특히 그것들이 흔하기 때문에, 그래서 학습 데이터에 자주 등장하기 때문이다.
LLM은 또한 πραγμα로는 학습할 수 없다. 이 문제에 대한 직관적인 반응은, 사전 프롬프트에 지침을 계속해서 더 많이 추가하고, 그 텍스트 파일을 LLM의 “기억”으로 취급하는 것인데, 하지만 그것은 그냥 통하지 않고, 아마도 앞으로도 통하지 않을 것이다. 문제 — “context rot” — 는 기술의 본성에 어느 정도 근본적으로 내재해 있다.
따라서 코드 생성기는 인간 코드 리뷰 파트너보다 더 적대적으로 다뤄야 한다. 그것이 오류를 만드는 것을 알아차리면, LLM이 사람처럼 아주 작은 컨텍스트 윈도 밖에서 의미 있게 실수로부터 학습할 수 없으므로, 그 코드에 대해 평가를 수행하는 기계적이고 결정론적인 하네스에 테스트를 항상 추가해야 한다. 그러니 피드백을 주는 것은 도움이 되지 않는다. 그저 코드를 다시 생성하라고 요청하는 것조차, 다시 전부를 리뷰해야 한다는 뜻이며, 앞에서 배웠듯 당신은 인간이기 때문에 한 번에 400줄 이상을 리뷰할 수 없다.
코드 리뷰는 사회적 프로세스이며, 당신은 그것을 그렇게 다뤄야 한다. 인간이 작성한 코드를 리뷰할 때는, 버그나 미충족 기술 요구사항을 공유하는 것만큼이나 지식과 격려도 공유하라.
LLM이 만든 코드를 리뷰해야 한다면, 자동화된 코드 품질 검증 도구를 강화하고, 다음번에는 품질 체크가 실패하는 즉시 그 에이전트 루프가 스스로 실패하도록 만들어라. 그것의 감정, 지식, 경험에 호소하는 함정에 빠지지 마라. 그것은 그런 것들을 가지고 있지 않다.
하지만 인간과 LLM 모두에 대해, 코드 리뷰 프로세스가 버그를 잡고 있다고 생각하는 함정에 빠지지 마라. 그건 코드 리뷰의 일이 아니다.
이 블로그에서의 내 글쓰기를 지원해 주시는 my patrons께 감사드린다. 여기서 읽은 내용이 마음에 들었고 더 읽고 싶거나, 내 various open-source endeavors를 지원하고 싶다면, support my work as a sponsor로 내 작업을 후원할 수 있다!
© Glyph 2025; Those Which Are Not를 제외하고 모든 권리 보유. 내 이해관계(재정적 이해관계 및 그 밖의 이해관계)에 대한 정보는 my disclosure statements를 참고하라.