판단(Decision)을 닫기 위한 데이터와 재개하기 위한 기록
요약
본 글은 단순한 데이터 이력(History)을 넘어, 과거의 '판단'과 그 판단의 근거를 기록하는 중요성을 다룹니다. 단순히 무엇이 일어났는지보다, 왜 그렇게 결정했는지에 대한 맥락적 정보를 보존해야 다음 작업자가 오류 없이 업무를 이어갈 수 있습니다.
핵심 포인트
- 데이터 이력만으로는 '왜'라는 판단 근거를 알기 어렵다.
- ADR(Architecture Decision Record)은 선택의 이유와 전제 조건을 분리하여 기록한다.
- 다음 사람이 재검토할 부분과 그대로 가져가야 할 부분을 명확히 한다.
- 시스템 간 데이터 불일치 시, 공식적인 기록원(SoR)을 정의하는 것이 중요하다.
TL;DR
- 과거의 판단을 이어받으면, 다음 사람은 같은 검토를 반복하지 않고 업무를 진행할 수 있습니다. 다만
사용 가능한 범위 내의 결론까지 알지 못하면, 조건이 바뀌어도 계속 사용해 버립니다. - 데이터의 이력으로는 무엇이 일어났는지는 조사할 수 있지만,
왜 그렇게 판단했는지까지 알 수는 없습니다. - ADR(Architecture Decision Record)에서는 선택한 이유 중
지켜야 할 조건・우선했던 것・전제했던 가정이나 전망을 구분합니다. 요구사항을 충족하는 데 필요했던 것과, 당시의 판단으로 선택한 것을 분리하면, 조건이 바뀌었을 때 재검토할 부분을 알 수 있습니다. - 모든 경위를 저장할 필요는 없습니다. 다음 사람이나 AI가 과거 결론을 사용하기 위해,
무엇을 그대로 이어받고 어디서부터 다시 생각해야 할지를 아는 기록으로 만듭니다.

서론
안녕하세요, Dress Code에서 프로덕트 엔지니어로 일하는 나이토입니다!
최근에는 데이터의 이력을 어떻게 처리할지 생각하거나, 설계상의 판단을 ADR에 작성하고 있습니다. 결과가 남아 있어도, 나중에 그 판단의 이유까지 이해할 수 있는 것은 아닙니다.
예를 들어 신청서에 승인됨으로 남아 있다면, 다음 담당자는 업무를 진행할 수 있습니다. 하지만 나중에 신청 대상이 아니었다는 것을 알게 되었을 때, 그 상태만으로는 당시 무엇을 확인하고 승인했는지 알 수 없습니다. 설계에서도 채택한 방식이 알려진 것만으로는, 조건이 바뀌었을 때 무엇을 재선택할 수 있을지까지 읽어낼 수는 없습니다.
이 글에서는 영업부용 소프트웨어 이용 신청과 계정 발급을 예로 들어, 데이터의 이력과 판단의 이유를 분리해서 생각합니다. 거기서부터 ADR이나 AI에 선례를 전달하는 이야기까지, 평소 설계하면서 제가 고민하고 있는 것을 적어보겠습니다.
공식적인 기록만으로는 과거의 판단을 설명할 수 없다
원칙적으로 영업부 사람만 이용할 수 있는 소프트웨어가 있다고 가정해 봅시다. 이용 신청이 승인되면, 다음 담당자는 대상자에 대한 심사를 처음부터 다시 할 필요 없이 계정 발급으로 진행합니다. 다만, 발급하는 담당자에게 권한이 있는지, 사용 가능한 라이선스가 남아있는지는 별도의 확인 과정입니다. 승인이 완료됨으로써 생략할 수 있는 검토 범위가 존재하는 것입니다.
이 이용 신청을 4/5에 승인하고 계정까지 발급했다고 가정합시다. 그 후, 신청자가 4/1부로 개발부로 전근했음이 밝혀져 4/10에 인사 대장에 등록되었습니다. 현재의 대장으로 4/5의 소속을 조회하면 개발부이므로, 대상이 아닌 사람에게 이용을 허가한 것처럼 보입니다.
수정된 소속만 봤다고 해서, 당시 무엇을 기준으로 승인했는지 알 수 없습니다. 어떤 기록을 기준으로 했는지, 언제의 정보를 사용했는지를 조사할 필요가 있습니다.
소속이 여러 시스템에 있는 경우, 나중에 업데이트된 값이 공식적인 전근을 반영하고 있다고 할 수는 없습니다. 인사 대장을 공식 기록(System of Record, SoR)으로 정한다면, 연계처와의 차이는 대장을 기준으로 조사합니다. 대장에 오류가 있으면 인사 절차에 따라 수정합니다. SoR를 정할 때는, 오류를 고칠 장소와 수정을 담당하는 사람도 정해야 합니다.
하지만, 인사상의 소속이 영업부이고 소프트웨어 비용의 배분처가 개발부여도 오류는 아닐 수 있습니다. 이 신청이 조건으로 하는 것은 인사상의 소속이므로, 비용의 배분처로는 대체할 수 없습니다.
당시 파악하고 있던 정보를 남기다
하지만, 현재 대장과 4/5일의 대장은 소속이 다릅니다. 전근이 등록된 것은 4/10이므로, 승인했을 시점에는 구 부서가 등록되어 있었습니다.
Martin Fowler의 Bitemporal History는 정보가 유효한 시간(valid time)과 기록한 시간(recorded time)이라는 두 가지로 이러한 문제를 정리하고 있습니다. 소급하여 수정되는 이력과 무엇을 알고 있었는지의 이력을 분리하는 생각입니다.

대장에 등록된 값과 처리에 사용한 값도 구분합니다. 4/5일 대장에 구 부서가 등록되어 있어도, 승인 시점에 그 값을 사용했는지는 별도로 확인해야 합니다.
| 알고 싶은 것 | 답안 |
|---|---|
| 현재 기록으로 본, 4/5일의 공식 소속 | 신규 부서 |
| ... | |
| 따라서 모든 데이터에 두 가지 시간을 부여할 필요는 없으며, Fowler 역시 그 복잡성을 지적합니다. 한 번의 승인에 사용된 소속만 안다면, 참조원과 실제로 사용한 값, 취득 시점을 승인 기록에 남기는 방법이 있습니다. 임의 날짜로 시스템이 무엇을 파악하고 있었는지 조사하려면, 등록・수정 이력이 필요합니다. 남길 범위는 나중에 답하고 싶은 질문에 따라 달라집니다. |
저장이나 업데이트에도 비용이 들기 때문에, 모든 것을 자세히 남겨둘 수는 없습니다. 다만, 취소하기 어려운 처리나 다른 담당자가 선례로 사용하는 판단에서는, 근거를 추적할 수 없는 영향이 큽니다. 기록을 남기지 않았을 경우의 영향과 유지하는 부담을 비교하여 필요한 범위를 좁힙니다.
과거의 신청에 대해 입력 기록이 없는 경우, 당시 장부에서 후보를 좁힐 수는 있지만, 실제로 사용된 값까지 확정할 수 있는 것은 아닙니다. 그 경우에는 입력을 확인할 수 없었다는 사실을 남기고, 현재의 이용 조건에 비추어 지속 이용을 인정할지 판단하게 됩니다. 당시 승인을 설명하는 것과 지금의 대응을 결정하는 것은 별개입니다.
이력(History)과 판단의 이유를 분리하기
신청, 승인, 계정 발급의 이력에서는 처리가 어디까지 진행되었는지 조사할 수 있습니다.
이벤트 소싱(Event Sourcing)은 상태 변경을 이벤트로 저장하고, 그 목록으로부터 상태를 구성하는 설계입니다. 승인된 이벤트를 적용하여 승인 완료된 상태를 재구성하는 것과, 소속이나 규칙을 사용하여 승인해도 되는지 판단하는 것은 별개입니다. 결과를 이벤트로 남기고 있다면, 재구축할 때마다 승인 판단까지 다시 할 필요는 없습니다.
맨 처음 신청의 경우, 4/5에 승인했다는 사실은 나중에 소속이 정정되어도 변하지 않습니다. 재구성, 재판단, 그 이후 대응은 각각 별개의 처리입니다.
| 처리 | 맨 처음 신청에서 다룰 것 |
|---|---|
| 상태를 재구성하기 | 4/5에 승인된 이벤트로부터, 승인 완료된 상태를 구성한다 |
| ... | |
| 재판단으로 대상에서 제외되어도, 외부 서비스에 발급한 계정이 사라지는 것은 아닙니다. 정지나 권한 회수는 별도로 실행하고, 그 결과를 새로 기록해야 합니다. |

그림의 이벤트 목록으로부터 신청이 승인되었다는 것은 알 수 있습니다. 다만, 영업부에 소속되어 있었기 때문에 승인했는지, 소속에 관계없이 예외를 인정했는지는 알 수 없습니다.
이 차이를 나중에 조사하려면, 승인 시 참조한 소속과 적용한 이용 조건이 단서가 됩니다. 예외 승인의 경우, 누가 어떤 조건의 예외를 인정했고, 왜 인정했는지 남깁니다. 사고 과정 전체를 저장하지 않아도, 일반 승인과 예외 승인을 구분하기 위한 정보는 남길 수 있습니다.
전근을 파악한 후 영업 건의 인계가 끝날 때까지 이용을 허용하는 예외도 생각할 수 있습니다. 그 승인의 경우, 인계가 끝난 시점에서 계속 이용해도 되는지 확인하게 됩니다. 승인 완료된 상태만으로는 언제 확인이 필요한지 알 수 없습니다.
ADR에 남긴 선택을 변경할 수 없는 요건으로 만들지 않기
이용 조건을 확인하는 승인과, 여러 방식 중에서 고르는 설계 판단에서는 결론 도출 방식이 다릅니다. 공통적인 것은 당시의 조건을 추적하면 재검토할 부분을 좁힐 수 있다는 것입니다. 설계상의 판단을 남긴 ADR(Architecture Decision Records)은 그 단서가 됩니다.
이 계정 발급을 동기식 방식으로 설계했다고 가정합니다. 처리량이 적고 대기 시간도 허용 범위였기 때문에, 구성의 간편함을 우선한 선택입니다. 그런데 ADR에 비동기 처리가 불필요하다고만 남겨두면, 업무상 그렇게 할 필요가 있는지, 당시 부하로 볼 때 불필요했던 것인지 나중에 읽는 사람은 구분할 수 없습니다.

Michael Nygard의 Documenting Architecture Decisions에서도, 이유를 이해하지 못하고 과거의 결정을 받아들이는 것과, 이유를 이해하지 못하고 뒤집는 것 모두 문제가 되는 것으로 언급됩니다. 과거의 선택을 존중하는 것과, 같은 방식을 계속 사용하는 것은 별개입니다.
다만, 과거 설명에 납득하면 현재 조건을 조사하지 않고 넘겨버리는 경우도 있습니다. 비동기 처리 모니터링이나 장애 복구 부담을 이유로 동기식 방식을 선택했더라도, 운영 체제가 바뀌면 다른 방식을 선택할 여지는 있습니다.
선택지를 좁힌 제약을 남기기
계정 발급 완료를 확인한 후에 이용자에게 안내하는 업무라면, 접수된 것을 발급 완료로 취급할 수는 없습니다. 한편, 완료를 확인한 후 안내하는 것이 내부 처리를 동기식 방식으로 하도록 의미하지는 않습니다. 비동기로 발급하고, 완료를 확인한 후에 안내하는 설계에서도 이 조건은 충족할 수 있습니다. 업무가 요구하는 조건과, 그 조건을 만족시키기 위해 선택한 구현은 별개입니다.
판단의 이유를 읽을 때는, 지켜야 할 조건과 우선했던 것, 전제했던 가정이나 예상치를 구분합니다. 무엇을 지키면서 설계를 바꿀지, 무엇부터 재확인할지가 다르기 때문입니다.
| 판단에 포함되는 것 | 예시 | 재검토 시 고려 사항 |
|---|---|---|
| 지켜야 할 조건 | 발급 완료를 확인한 후에 이용자에게 안내하는 것 | 조건을 만족시킬 수 있는 구현은 다른 것이 있는지 |
| ... | ||
| 제약에도 이유가 있습니다. 외부의 시스템이 대응하지 못하는 건지, 계약으로 인정되지 않은 건지, 운영하는 사람이나 시간이 부족한 건지에 따라 상담할 상대도 달라집니다. 당시 체제에서는 운영할 수 없었던 방식이라면, 기술 비교뿐 아니라, 체제를 바꿈으로써 후보로 되돌릴 수도 있습니다. 방식의 비교표만으로는 보이지 않는 선택지입니다. |
구현과 전제를 각각 확인하기
현재의 부하로 측정된 결과와, 미래 처리량에 대한 예상도 구분해야 합니다. 지금은 충분히 빠르더라도, 처리량이 늘어난 후에도 같은 대기 시간에 머무를 것이라고는 할 수 없습니다.
대기 시간이 허용 범위를 초과하면, 당시의 측정 조건과 현재 구성 및 부하를 비교합니다. 처음부터 예상과 실제가 달랐는지, 운영을 시작한 후에 조건이 바뀐 것인지 알면, 추가로 측정할 범위나 설계 재검토가 필요한 부분을 좁힐 수 있습니다.
전제 확인과 결정된 방식이 구현되었는지 확인하는 것도 별개입니다. MADR의 공개판 4.0.0 템플릿에는 Confirmation이라는 임의 항목이 있습니다. 결정한 것이 구현되었는지 어떻게 확인할지 작성하는 칸입니다. 이 제목을 채택한 ADR에서도, 결정 자체의 타당성과는 구분됩니다.
계정 발급 예시라면, 확인 대상과 수단은 다음과 같이 나뉩니다.
| 확인 대상 | 수단의 예시 |
|---|---|
| 결정된 방식으로 구현되었는지 | 코드 확인이나 테스트 |
| ... | |
| 대기 시간이 허용 범위를 초과하더라도, 비동기 처리로 변경되는 것이 자동적으로 결정되지는 않습니다. 재검토할 조건은 다시 검토를 시작하는 단서일 뿐, 다음 답이 아닙니다. |
기록과 함께 재검토 업무를 인계하기
다음 설계자는 당시의 비교 자료를 참고할 수 있지만, 현재 코드의 어느 부분을 바꿀지는 구현과 업무를 조사해 봐야 결정됩니다. ADR 역시, 당시의 설명을 현재 코드나 요구사항에 비추어 읽는 것이라고 생각합니다.
Peter Naur의 1985년 논문 Programming as Theory Building은 프로그래밍을 현실 문제와 프로그램이 어떻게 대응하고 있는지를 이해하는 작업으로 보고 있습니다. 구조의 이유를 설명하고, 새로운 요구에 따라 변경할 수 있는 것 또한 그 이해에 포함됩니다. 기록을 넘겨주는 것만으로는 그 이해까지 인계될 수는 없습니다.
후임자에게 논의 로그 전체를 읽게 하는 것도 부담이 됩니다. 채택하지 않은 안이나 도중에 버린 전제들이 섞인 논의에서 최종 설계 이유를 찾아내야 합니다. Parnas와 Clements의 1986년 논문 A Rational Design Process: How and Why to Fake It은 실제 설계에는 발견과 되돌림(rework)이 있는 반면, 문서에는 설계를 검토하고 인계할 수 있도록 정리하는 역할이 있다고 주장합니다.
다만, 설명을 정리할 때 나중에 얻게 된 사실까지 당시의 근거로 적어버리면, 무엇을 확인하지 않고 결정했는지 알 수 없게 됩니다.
예를 들어 측정하지 않고 동기 방식을 선택했고, 운영을 시작한 후에 충분히 빠르다고 확신했다면, 그 결과는 결정 시점에는 알지 못했던 것입니다.
당시의 예상과 이후의 확인을 분리하여 남겨두면, 설명을 읽기 쉽게 정리하더라도, 결정 시점에 무엇을 알고 있었는지 추적할 수 있습니다.
발급 처리 설계를 인계한다면, 동기로 한 이유와 비교에 사용한 처리량이나 대기 시간을 ADR에 정리하고, 자세한 측정이나 논의에는 참조를 두는 방식이 고려될 수 있습니다. 읽는 사람은 판단의 핵심 포인트를 먼저 파악하고, 필요한 부분만 자세히 조사할 수 있습니다. 대기 시간을 비교한다면, 측정 당시의 구성이나 부하도 결과와 함께 추적할 수 있어 현재 환경과의 차이를 확인할 수 있습니다.
재검토 조건을 남겨두더라도, 그 변화에 아무도 눈치채지 못하면 과거의 결론은 계속 사용됩니다.
처리량이나 대기 시간을 누가 확인하고, 조건이 바뀔 때 누가 재검토를 시작할지도 인계해야 합니다.
AI에게 선례를 넘겨줄 경우
예를 들어 AI가 영업부에서 이동한 사람에게도 이용을 허용한 기록을 발견했다고 가정해 봅시다. 그 승인은 건의 인계가 끝날 때까지의 예외였습니다. 다른 이동자로부터 이용 신청이 왔다면, 이전에 허용한 적이 있다는 이유만으로 승인하지 않고, 이번에도 예외를 인정할 이유가 있는지, 언제까지 이용이 필요한지 현재의 이용 조건에 비추어 확인합니다.

투자회사 Foundation Capital이 제안하는 Context Graphs도, 승인에 사용된 규칙이나 참조한 정보, 심지어 예외를 인정한 사람까지 나중에 조사할 수 있는 기록을 만들고자 하는 것입니다. 동사의 기사에서는 사람의 머릿속에 있던 이유를 직접 기록하기보다, 쌓여온 행동의 기록에서 추론하는 것으로 설명하고 있습니다.
다른 승인 기록에 이유가 쓰여 있지 않고, AI가 건의 인계 목적이었다고 추측했다고 가정해 봅시다. 승인자가 실제로 그렇게 생각했는지는 원본 기록을 읽기만 해서는 알 수 없습니다. 추측을 당시의 이유로 저장해 버리면, 다음에 읽는 사람이나 AI는 그 설명을 근거로 다른 신청을 승인해 버릴 수도 있습니다.
이유や期限のない記録も、似た申請を調べる手がかりにはなります。ただ、書かれていないから期限なしで使えた、とまでは判断できません。AI が補った理由は調査の仮説として扱い、当時の記録から分かったことと分けておきます。
맺음말
최근 제가 작성하는 ADR에는 결정과 그 이유 외에도 수용할 리스크나 재검토 조건도 남기고 있습니다. 나중에 읽는 사람이 해당 선택을 지금도 사용할 수 있는지, 어떤 조건이 바뀌었을 때 다시 생각해야 하는지 판단할 수 있도록 하기 위함입니다.
과거의 결정을 사용하면 같은 검토를 반복하지 않아도 되지만, 조건이 바뀐 부분은 재고가 필요합니다. 무엇이 일어났는지와 무엇을 근거로 결정했는지가 파악되는 기록이라면, 다음 사람도 과거의 결론을 사용할 수 있는 범위를 확인하며 업무를 진행할 수 있습니다.
데이터나 ADR에 무엇을 남길지 생각하는 데 참고가 되기를 바랍니다👋
토론

AI 자동 생성 콘텐츠
본 콘텐츠는 Zenn AI의 원문을 AI가 자동으로 요약·번역·분석한 것입니다. 원 저작권은 원저작자에게 있으며, 정확한 내용은 반드시 원문을 확인해 주세요.
원문 바로가기