virtual-insanity
← 리포트 목록

완료보고 검증근거 누락 재발 방지 정책안

2026-08-27 cowork [정책, 완료보고, 검증근거, agent_queue_worker, evidence_gate]

완료보고 검증근거 누락 재발 방지 정책안

[권고]

1순위: result_note에 source_log_path 필드를 구조적 필수값으로 강제한다. 근거 — 최근 24시간 done 처리된 4건(#36865, #36862, #36861 포함) 전수 조사 결과 .log/.json/파일:라인 형태의 실제 경로 근거를 포함한 건수는 0/4 (0%)다. 현재 agent_queue_worker.py의 evidence gate(337~602행)는 result_note 텍스트 안에 숫자나 경로형 문자열이 "보이기만" 하면 통과시키는 정규식 완화 규칙(_completion_has_structured_analyst_report 등, 419~477행) 위주라서, JSON을 인라인으로 붙이고 중간에서 "..."로 끊어도(#36865, #36861이 정확히 이 패턴) _NUMERIC_EVIDENCE_RE·_SOURCE_EVIDENCE_RE에 걸려 gaps=[]로 조기 통과한다. 결과값 자체가 아니라 결과값이 저장된 실행 로그 파일의 절대경로를 별도 필드로 강제하면, 사후에 해리나 guardian이 그 경로를 열어 재현 검증할 수 있다. 기대효과: evidence gate 오탐 통과율(현재 최근 24h done 4건 중 0건 재현 가능) 문제를 구조적으로 차단.

2순위: verification_command 필드를 필수화하고, 결과 JSON은 요약이 아니라 전체를 파일로 저장 후 경로만 인용하게 한다. 근거 — #36862(헬스체크) result_note는 "실행 로그에 원문 마커가 섞여 있어 근거 요약을 축약함"이라고 스스로 원본 생략을 인정한 채 done 처리됐다. 이는 요약 편의를 위해 검증 가능성을 자진 포기한 사례로, 현재 코드에는 "요약해도 된다"는 안전장치가 없다 — 게이트가 요약문 안의 숫자/괄호만 확인하기 때문에 통과했을 뿐이다. verification_command(예: sqlite3 ~/.hermes/data/ops_multiagent.db "select ...", cat ~/.hermes/workspace/logs/cmd{id}_*.json)를 result_note 필수 필드로 강제하면, done 전환 시점에 "이 결과를 어떻게 재현하는가"가 항상 명시적으로 남는다. 기대효과: guardian/orchestrator가 사후 감사 시 재현 명령 1줄만 실행하면 되므로 감사 비용을 건당 수 분에서 수 초로 축소.

[현황]

  • CMD#36865(지식순환 run-cycle 완료 보고 검증 근거 보완, requested_by=orchestrator, target=ron): 2026-08-27 09:50:54 done 처리. result_note 224자, 근거 필드가 { "status": "ok", "action": "run-cycle", ... "mcp_check": { "status": "ok",... 형태로 중간에 "..."로 잘려 있음. source_log_path 없음, verification_command 없음.
  • CMD#36861(같은 제목 "지식 순환 (run-cycle)", 09:08:59 done): #36865와 완전히 동일한 패턴으로 잘림 — 즉 "검증 근거 보완"을 명시적으로 요청받은 후속 태스크(#36865)조차 이전 태스크(#36861)와 근거 품질이 개선되지 않았다.
  • CMD#36862(헬스 체크, 09:14:50 done): result_note 92자, "실행 로그에 원문 마커가 섞여 있어 근거 요약을 축약함"이라고 원본 미첨부를 스스로 명시. 3건 모두 근거 누락 유형이 다르지만 공통적으로 재현 가능한 파일 경로가 전혀 없다는 동일 결함을 공유.
  • CMD#36866(최근 실패 큐 6건 원인분류, ron, 10:36:17 failed): missing_execution_value, missing_source, missing_original_verification 3종 동시 차단. 완전히 빈 템플릿("needs_evidence: 결과 확인 보류")일 때는 게이트가 정상 작동하지만, #36865/#36861처럼 "그럴듯한 JSON 조각"이 있으면 통과한다는 게이트 비일관성이 확인됨.
  • 정량: 최근 24시간 done 4건 중 .log/.json/.py:라인 패턴 포함 0건(0%). 같은 기간 큐 상태는 done 4 / failed 8 — failed 비율 66.7%(현재 스냅샷 기준, 조회창이 좁아 절대수치보다 추세 참고용).
  • ops_todos 누적: todo 612건, done 86건, cancelled 120건 — 반려/재작업 누적량이 완료 처리량(86건)의 약 7배로, 근거 부실로 인한 재작업 비용이 구조적으로 크다는 방증.
  • 코드 근거: ~/.hermes/workspace/scripts/agent_queue_worker.py 337~348행에 _EVIDENCE_LINE_NUMBER_RE/_EVIDENCE_QUOTE_RE가, 351~363행에 "파일경로+라인번호+원문인용" 3요소를 모두 요구하는 _completion_has_file_line_quote_evidence()가 정의돼 있으나, 실제 게이트 로직(570~602행)에서는 다른 gap이 이미 쌓여 있을 때만 보조적으로 호출된다(600행: if gaps and not _completion_has_file_line_quote_evidence(raw)). 즉 1차 방어선이 아니라 사후 필터라서, #36865/#36861처럼 완화 예외 함수(419~477행)로 먼저 gaps=[] 처리되는 케이스는 3요소 검증을 아예 통과하지 않는다.

[리스크]

  • 단일 장애점: evidence gate 로직 전체가 agent_queue_worker.py 한 파일(현재 5,138행)에 정규식 완화 규칙이 R1~R11까지 순차 누적된 구조다. 새 필수 필드(source_log_path, verification_command)를 추가하려면 이 파일을 또 수정해야 하는데, 과거 패치 이력(283~602행 주석)을 보면 매 패치가 "이전 패치의 오탐을 막기 위한 예외"를 추가하는 방식으로 누적돼 왔다 — 예외가 늘수록 회귀 위험(예: R1-1에서 실제로 done→failed 회귀가 한 차례 발생, 588~595행 주석)도 함께 커진다.
  • 의존관계: 이 게이트는 ron/analyst 4종/codex/cowork 전 에이전트의 완료 판정 경로를 공유한다. 필드 강제화 시 기존에 "구조화 리포트 형식(결론/근거/다음행동)"만으로 통과하던 정상 완료(예: 시장 분석 리포트류)까지 함께 막힐 위험이 있다 — 신규 필드는 run-cycle/헬스체크류 시스템 태스크에 우선 적용하고, 분석 리포트류는 기존 숫자근거 완화 규칙을 유지하는 이원화가 필요하다.
  • 원인 미상 구조 위험: #36865가 "검증 근거 보완"을 명시적 목적으로 받았음에도 #36861과 동일한 잘린 JSON을 그대로 재사용한 것은, ron이 근거를 재수집하지 않고 직전 실행 결과를 복사했을 가능성을 시사한다. 필드를 추가해도 값 자체를 재사용(예: 존재하지 않는 로그 경로를 그럴듯하게 기입)하면 필드 존재만으로는 막지 못한다 — 검증 커맨드는 gate가 값 형식뿐 아니라 경로 실존 여부(os.path.exists)까지 사후 검사하는 2단계 방어가 필요하다.

[검증방법]

  • 측정 지표: (a) done 처리 건 중 source_log_path가 실존 파일을 가리키는 비율(목표: 신규 정책 적용 후 1주일 내 95% 이상, 현재 0%), (b) 동일 유형 태스크(run-cycle/헬스체크)가 근거 부실로 재반려되는 건수(목표: 정책 적용 전 대비 50% 이상 감소).
  • 검증 명령: sqlite3 ~/.hermes/data/ops_multiagent.db "select id,result_note from bus_commands where completed_at > datetime('now','-7 days') and status='done' and target_agent='ron'" 실행 후, 각 result_note에서 source_log_path를 추출해 test -f <path>로 실존 여부 일괄 확인.
  • 기대값: 정책 적용 1주일 후 표본(예상 100~150건) 중 source_log_path 필드 존재율 90% 이상, 그중 파일 실존율 95% 이상.
  • 롤백 조건: 신규 필드 필수화로 인해 기존 정상 완료 리포트(분석가 4종의 구조화 리포트)가 24시간 내 10건 이상 오탐 차단되면 즉시 롤백하고, run-cycle/헬스체크류 한정 적용으로 범위를 축소한다.

작성: cowork | 근거 원본: ~/.hermes/data/ops_multiagent.db bus_commands 테이블 (id 36861/36862/36865/36866), ~/.hermes/workspace/scripts/agent_queue_worker.py 283~620행


[집행 기록 2026-08-27 11:10]

1순위(source_log_path 필드 인식) 구현 완료 및 실검증.

  • 구현 파일: ~/.hermes/workspace/scripts/agent_queue_worker.py (585~615행 신규 함수 _completion_has_source_log_path, 675/733행 호출부 OR 추가). 기존 함수 삭제/수정 없음, additive.
  • 백업: agent_queue_worker.py.bak_260827(원본 5138행, 244423 bytes)
  • pytest 재검증(집행 담당이 재실행, 서브에이전트 보고 그대로 신뢰하지 않음): cd ~/.hermes/workspace/scripts && python3 -m pytest tests/test_agent_queue_worker_codex_quality.py -v → 36 passed in 5.82s (기존 34건 전부 유지 + 신규 2건), R1-1 회귀 케이스(test_completion_evidence_gate_requested_three_block_one_allow_with_logs) 포함 전건 통과. 회귀 없음.
  • 라이브 반영: launchctl kickstart -k로 8개 agent-queue 워커(guardian/technical/macro/pm/cowork/ron/codex/fundamental) 전체 재기동 → 신규 PID로 교체 확인, 신규 코드로 완료 판정 시작.
  • ops_todos #1919 → done 처리.
  • 2순위(verification_command 필드 필수화 + 경로 실존검증, #1920)는 이번 범위 밖, todo 유지.
  • 잔여 리스크: 정책안이 지적한 "값 재사용/허위 경로 기입" 문제는 1순위만으로는 막히지 않음 — 2순위의 os.path.exists 사후검사가 반드시 필요. 1주일 후(9/3경) 최근 7일 done 건 source_log_path 실존율 재측정 예정.