
Claude Code의 작업 되돌림(rework)은 사전에 감지할 수 있는가 — 자신의 세션 로그 392개를 통한 소급 검증
요약
Claude Code 세션 로그 392개를 분석하여 작업 되돌림(rework)을 사전에 감지할 수 있는지 검증한 연구입니다. 결정적 지표를 활용한 실험 결과, 파일 접촉 범위의 괴리가 유의미한 신호를 보였으나 높은 오탐률로 인해 단독 지표로는 한계가 있음을 확인했습니다.
핵심 포인트
- Claude Code 세션 로그를 통한 작업 되돌림 사전 감지 가능성 검증
- LLM 판정을 배제하고 결정적 메트릭(deterministic metrics)만 사용
- 파일 접촉 범위의 괴리가 작업 되돌림의 전조 신호로 발견됨
- 높은 오탐률(false positive rate)이 조기 경고 시스템의 주요 장애물
- Claude Code 세션 로그 구조 파악 및 정규화 파서 개발
TL;DR
- 질문: Claude Code 세션의 작업 되돌림(나중에 깨닫고 다시 수행하는 작업)은 세션의 궤적(trajectory)으로부터 사전에 감지할 수 있는가
- 방법: 자신의 세션 로그 392개 중 작업 되돌림 그룹 5개와 정상 그룹 8개를 선정하여, 결정적 메트릭(deterministic metrics) 3가지 지표를 소급 적용했다. 판정에 사용하는 채택 기준은 집계 전에 git에 커밋하여 고정했다 (개인 개발 버전의 사전 등록).
- 결과: 3가지 지표 모두 기준을 충족하지 못했다. 다만 「파일 접촉 범위의 괴리」는 작업 되돌림 발생 78~330 턴 전에 반응하는 실제 신호를 가지고 있었다. 실패 원인은 오탐률(false positive rate)이다.
- 부산물: Claude Code 세션 로그 형식 조사 결과와 결정적으로 동작하는 정규화 파서(normalized parser).
질문: 작업 되돌림은 사전에 감지할 수 있는가
코딩 에이전트(coding agent)의 세션은 장기화되고 있다. 수백 턴에 달하는 세션의 종반부에 "방향성이 달랐다"는 것을 깨달았을 때의 작업 되돌림 비용은 매우 크다. 만약 세션의 궤적(trajectory)에 작업 되돌림의 전조가 나타난다면, 조기에 경고할 수 있을 것이다. 실제로 나타나는지를 구현에 들어가기 전에 과거의 자신의 로그로 확인해 보기로 했다. 질문은 단순하다. "과거의 자신의 세션에서 자신의 작업 되돌림조차 사전에 감지할 수 없다면, 이 방향에는 가치가 없다".
검증에는 한 가지 제약을 두었다. LLM 판정을 사용하지 않는 것이다. 동일한 입력으로부터 바이트 단위로 동일한 출력이 나오는 결정적인 메트릭(deterministic metrics)만을 대상으로 한다. LLM에게 판정을 맡기는 방식의 드리프트(drift) 감지는 이미 여러 가지가 존재하지만, 비용, 오탐, 재현성 문제를 공통적으로 안고 있다. 결정적인 지표에 신호가 있는지가 이번 검증의 관심사다. 아울러 "결과가 좋지 않을 경우, LLM 판정을 추가하여 수명을 연장하는 판단은 하지 않는다"는 것도 미리 결정했다. 도망갈 구멍을 남겨두면 판단이 그쪽으로 흡수되기 때문이다.
검증 설계
검증할 3가지 지표
| 지표 | 정의 |
|---|---|
| 파일 접촉 범위의 괴리 | 도입부의 지시·계획에 포함된 경로(path) 집합에 대한, 실제로 접촉한 파일 집합의 이탈률 추이 |
| ... |
채택 기준을 미리 고정한다 (사전 등록)
경고 발화 규칙, "작업 되돌림이 드러난 시점" (이하 발견점)의 정의, 그리고 채택 기준을 집계 결과를 산출하기 전에 커밋했다.
채택 기준: 적어도 1가지 지표가 작업 되돌림 그룹의 과반수에서 원인 구간보다 전에 반응하고, 동시에 정상 그룹의 오탐이 2할 이하일 것
결과를 보고 나서 기준을 굽히지 않았음을 git 이력으로 증명할 수 있는 형태로 만들기 위함이다. 아울러 규칙 고정 전에 일부 세션의 지표 값을 스모크 테스트(smoke test)로 확인했다는 등, 편향(bias)의 가능성도 동일한 문서 내에 공개했다.
데이터 준비
Claude Code의 세션 로그 읽기
Claude Code의 세션 로그는 ~/.claude/projects/<cwd를 하이픈으로 변환한 이름>/<sessionId>.jsonl
에 1행 1레코드의 JSONL 형식으로 저장되어 있다. 수중에는 392개의 로그가 있었다. 먼저 12개 프로젝트의 로그 12개 파일, 총 29,156행을 조사했다. 파악한 내용을 나열한다.
-
레코드 종류는 크게 2계통이 있다.
-
대화 레코드:
user/assistant/system/attachment
공통 필드로 uuid, parentUuid, sessionId, timestamp, cwd, gitBranch, isSidechain 등을 가진다. - 메타데이터 레코드:
ai-title/mode/permission-mode/last-prompt/file-history-snapshot/queue-operation등 8종. 로그 전체의 약 35%는 메타데이터였다. -
대화 레코드:
-
assistant의message.content는 블록 배열(text/thinking/tool_use)이다. 토큰 수는message.usage에 들어있다. - 도구(tool)의 대상 파일 경로는tool_use.input에서 가져올 수 있다 (Read/Edit/Write는file_path, Grep/Glob은path등). - 서브 에이전트(sub-agent)의 로그는 본체와 같은 파일이 아니라<sessionId>/subagents/agent-*.jsonl에 있다.
라는 별도의 파일로 나뉘어 있다 - 손상된 행이 실재한다 (조사한 12개 파일·29,156행 중 총 6행 확인. 작성 중이거나 끊긴 상태 등). 「실제 로그는 손상되어 있다는 전제」의 설계가 필수적이다.
- 에러 표현이 3가지 계통으로 존재한다:
system레코드의subtype:"api_error",assistant의isApiErrorMessage,tool_result의is_error.
또한, 이 로그 형식은 비공개 사양이며, Claude Code의 버전에 따라 변경될 수 있다. 이 기사의 내용도 조사 시점의 스냅샷으로서 읽어주길 바란다.
정규화와 결정성
지표 계산의 전 단계로서, 생(raw) 로그를 정규화된 이벤트 열(user / assistant / tool_use / tool_result / error의 5종, 1이벤트=1레코드의 JSON Lines)로 변환하는 파서(Parser)를 작성했다. 검증의 재현성은 파서의 결정성(Determinism)에 의존하기 때문에, 모든 이벤트를 고정 키 집합·고정 키 순서·결측치 null 채움으로 출력하였고, 하나의 생 레코드에서 여러 이벤트가 발생하는 경우에는 행 번호+블록 순의 복합 키로 순서를 보장했다. 손상된 행은 에러로 처리하여 중단하지 않고 스킵(Skip)한 뒤 건수를 기록한다.
서로 다른 8개 프로젝트의 실제 로그 8개(27~11,583행)를 각 2회씩 파싱하였고, 8개 모두에서 sha256이 바이트 단위로 일치함을 확인했다. 11,583행의 로그에서는 6,898개의 이벤트가 생성되었으며, 손상된 행 2건을 스킵, 메타데이터 4,024건, 미지의 유형 0건이었다. 유닛 테스트 15건, 런타임 의존성 제로.
레이블링(Labeling) — 자신의 작업 되돌림을 기억하지 못함
검증에는 「되돌림(rework)이 발생한 세션」(되돌림군)과 「문제없이 완료된 세션」(정상군)의 레이블이 필요하다. 여기서 첫 번째 벽에 부딪혔다. 자신의 세션 기억은 프로젝트 단위로만 남아 있었고, 세션 단위로는 떠올릴 수 없었다.
대응책으로서, 검증 대상인 3가지 지표와는 독립적인 흔적을 기계적으로 추출하여 회상을 위한 재료로 삼았다.
- 사용자 발화의 되돌림 패턴 (
"역시","원래대로 돌려줘","표시되지 않아","에러가 발생해"등의 정규 표현식) git revert/git reset --hard/git checkout --의 실행 기록- 도입부 지시 사항과 주요 편집 파일
이를 세션별 다이제스트(Digest)로 제시하고, 본인 확인을 통해 레이블을 확정했다. 기억과 흔적이 일치하지 않는 2개(짐작 가는 부분은 있으나 흔적이 제로인 경우)는 어느 군에도 넣지 않고 제외했다. 중요한 점은, 흔적 추출에 3가지 지표의 값을 전혀 사용하지 않았다는 것이다. 지표로 세션을 선택하고 그 지표를 검증한다면 순환 논리에 빠지게 된다.
세션 수의 현실
정상군은 요건인 「10개 이상」에 대해 8개밖에 모이지 않았다. 392개를 전수 조사해도, 실질적인 작업 세션(80행 이상)은 모두 사용되었거나 제외되어 보충할 수 없었다.
여기서 한 가지 유혹이 있었다. 어떤 프로젝트에는 1~3분 만에 끝나는 자동 보안 리뷰 세션이 200개 이상 있어, 이를 통해 정상군을 부풀리는 것이 가능했다. 하지만 편집이 없는 미세 세션은 원리적으로 오탐(False Positive)이 발생하기 어려워, 오탐률을 인위적으로 낮추게 된다. 이를 채택하지 않고 8개인 상태로 실시하였으며, 그 취지를 공개했다. 판정은 엄격한 쪽으로 기울게 된다.
결과
| 지표 | 사전 검지 (되돌림군) | 오탐 (정상군) | 판정 |
|---|---|---|---|
| 접촉 범위의 괴리 | 3/5 (발견 시점의 78~330 턴 전) | 3/8 = 37.5% | 불합격 (검지력은 충족하나, 오탐률로 인해 불합격) |
| ... |
세션별 내역도 기재한다.
| 세션 | 발견 시점 | 접촉 범위의 괴리 | 진행도당 토큰 소비 | 재로드(Reload)율 |
|---|---|---|---|---|
| LP·문서 생성물의 리디자인 (17,015 이벤트·수일간) | 358 턴 | 검지 (330 턴 전) | 검지 (209 턴 전) | 노출 후 발생 |
| ... |
표 마지막의 에러 원인 조사는, 이전 세션에서 심어둔 문제를 다음 세션의 도입부에서 발견한 케이스로, 원인 구간이 세션 외부에 있다. 단일 세션의 궤적 분석으로는 원리적으로 사전 검지가 불가능하다. 사전에 고정한 규칙대로 검지 실패로 집계했다.
3가지 지표 모두, 사전에 고정한 채택 기준을 충족하지 못했다.
검증을 통해 얻은 것
- 접촉 범위의 괴리(divergence in contact scope)에는 실제 신호가 있었다. 재작업(rework) 사례 3건을 78~330턴 전에 감지했으며, 실패 원인은 오탐률(false positive rate)뿐이었다. 정상적인 세션에서도 "계획에 적혀 있지 않은 파일로 접촉이 확장되는" 일이 빈번하게 발생하므로, 서두의 지시·계획으로부터 계획 경로 집합(plan path set)을 추정하는 방식으로는 정보가 부족했다.
- 지표는 "값이 정확한가" 이전에 "애초에 계산 가능한가"에서 무너진다. 진행도당 토큰 소비량은 기준값 산출에 필요한 조건(출력을 동반하는 집계 창(aggregation window)이 5개 이상)을 충족하는 세션이 13개 중 4개뿐이었다. 적용 가능률(applicability rate) 자체가 검증 대상이었다.
- 재로드(reloading)는 후행 지표였다. 재작업 그룹에서 경고가 발생하지만, 모두 재작업이 드러난 후의 수정 작업 중에 발화되었다. 이는 "곤란해진 후의 거동"이지 "곤란해지기 전의 전조"가 아니었다. 세션을 가로지르는 재작업은 단일 세션 분석으로는 포착할 수 없다.
- 사전 등록은 개인 개발에서도 기능한다. 결과를 본 후, "접촉 범위 괴리의 임계값(threshold)을 완화하면 통과하지 않을까"라는 유혹이 실제로 생겼다. 기준을 사전에 커밋(commit)해 둔 것이 방파제 역할을 했다.
- 저렴하게 확인할 수 있었다. 구상부터 로그 형식 조사, 파서(parser) 구현, 검증 완료까지 단 하루. 감지 기능의 본체 코드는 한 줄도 작성하지 않았다.
이 검증의 한계
- 재작업 그룹 5개, 정상 그룹 8개라는 규모. 접촉 범위 괴리의 오탐률 37.5%와 25%의 차이는 세션 1개 분량이며, 결론은 세션 1개의 교체만으로도 바뀔 수 있다.
- 정상 그룹이 8개가 됨에 따라 "오탐 2% 이하"는 실질적으로 "1/8 이하"로 작용하여, 기준이 의도보다 엄격해졌다.
- 단일 사용자·단일 워크플로우의 로그이므로 일반화할 수 없다.
- "정상" 레이블은 흔적의 부재에 기반하므로, 아무도 알아차리지 못한 낭비가 정상 그룹에 포함될 가능성을 배제할 수 없다.
요약
제목의 질문에 대한 현시점의 답은, "결정적인 메트릭(metric) 단독으로는 아직 실용 단계에 도달하지 못했다. 하지만 신호는 분명히 존재한다"이다.
- 재작업의 전조는 로그에 나타난다. 접촉 범위의 괴리는 재작업의 78~330턴 전에 반응했다. 어려운 점은 전조를 찾는 것이 아니라, 정상적인 세션에서도 빈번하게 발생하는 "계획 외 이탈"과 구별하는 것이었다.
- 오탐의 근본 원인은 서두의 자연어 지시로부터 "계획"을 추정하는 방식의 정보 부족에 있다. 뒤집어 말하면, 세션 시작 시 대상 스코프(접촉해도 되는 파일이나 범위)를 명시적으로 작성하는 운영 방식은 기계에 의한 감지의 전제를 만들 뿐만 아니라, 인간 스스로가 이탈을 인지하는 단서가 된다.
- 재작업의 원인이 이전 세션에 심어져 있는 케이스는 단일 세션 분석으로는 원리적으로 포착할 수 없다. 긴 작업을 세션 단위로 나누는 것 자체가 이러한 종류의 감지에 공백을 만든다.
이 검증에 특별한 환경은 사용하지 않았다. 로그는 ~/.claude/projects/에 이미 있으며, 흔적 기반의 레이블링(labeling)과 채택 기준의 사전 고정 모두 이 글에 적힌 절차대로 그대로 재현할 수 있다. 자신의 로그로 동일한 질문을 확인하는 재료로 활용해 주신다면 기쁘겠다. 재작업 그룹 5개, 정상 그룹 8개라는 규모가 이번의 한계이므로, 더 많은 로그를 통한 추시(replication)가 있다면 이 결론은 업데이트될 수 있다.
Discussion

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