상태: 검토 전 입력 범위:
sample-session-batch.jsonlturn 0–3 결론 신뢰도: 원인·변경·합성 검증은 확인됨, 실제 장애 트래픽은 확인 필요
30초 인수인계
| 항목 | 인수인계 내용 |
|---|---|
| 증상 | 배치 재시도 뒤 동일 안내가 두 번 발송됐다. |
| 원인 | 같은 업무 이벤트에도 재시도마다 새 request_id가 생겨 기존 중복 방지 조건을 통과했다. |
| 결정 | invoice_id + notice_type 조합을 멱등 키로 사용하고 유니크 제약을 적용했다. |
| 검증 | 합성 재시도 20회에서 추가 발송은 0건이었다. |
| 남은 한계 | 실제 장애 트래픽의 24시간 관찰은 수행하지 않았다. |
문제 경계
- 기대 상태: 같은 업무 이벤트가 재시도돼도 안내는 한 번만 발송돼야 한다.
- 실제 상태: 요청 단위 ID가 바뀌면서 같은 업무 이벤트가 새 발송으로 처리됐다.
- 이번에 확인한 범위: 재시도 전후의 발송 키, 업무 이벤트 멱등 키, 합성 재시도 20회.
- 이번에 확인하지 않은 범위: 실제 장애 트래픽에서의 24시간 재발 여부.
확인된 사실
- [확인됨] 같은 업무 이벤트의 재시도마다 새
request_id가 생성됐다. (turn 1) - [확인됨] 업무 이벤트 키에 유니크 제약을 적용했다. (turn 3)
- [사용자 결정] timeout 증가는 원인과 무관해 제외했다. (turn 2)
판단 기록
채택한 결정
전송 요청의 일회성 식별자가 아니라 invoice_id + notice_type으로 표현되는 업무 이벤트를 중복 판단 기준으로 사용한다. 재시도로 요청이 다시 만들어져도 같은 안내라는 업무 의미는 바뀌지 않기 때문이다.
배제한 선택
timeout 증가는 채택하지 않았다. 대기 시간을 늘려도 재시도마다 새 요청 ID가 생기는 구조는 그대로여서 중복 발송의 직접 원인을 제거하지 못한다.
실행 또는 재현 절차
| 단계 | 행동 | 기대 신호 | 실행 상태 |
|---|---|---|---|
| 1 | 같은 업무 이벤트의 재시도 전후 request_id를 비교한다. |
업무 내용은 같지만 요청 ID가 달라지는 표본이 확인된다. | 확인됨 · turn 1 |
| 2 | invoice_id + notice_type 조합을 멱등 키로 사용하고 유니크 제약을 적용한다. |
동일 업무 이벤트가 두 번째 발송 대상으로 저장되지 않는다. | 확인됨 · turn 2–3 |
| 3 | 동일 이벤트를 합성 환경에서 20회 재시도한다. | 추가 발송 횟수가 0건으로 관찰된다. | 확인됨 · turn 3 |
| 4 | 실제 장애 트래픽을 24시간 관찰한다. | 재발 건수와 키 충돌 처리 결과가 기록된다. | 권장·미검증 |
검증 경계
| 검증한 것 | 범위 | 관찰 결과 | 증명하지 못한 것 |
|---|---|---|---|
| 업무 이벤트 멱등 키 적용 후 재시도 | 합성 재시도 20회 | 추가 발송 0건 | 실제 장애 트래픽 24시간 안정성, 다른 안내 유형에 대한 일반화 |
남은 위험과 후속 작업
- [확인 필요] 실제 장애 트래픽의 24시간 중복 발송 재발 건수.
- [확인 필요] 다른
notice_type에서도 업무 식별자 조합이 충분한지 여부.
출처 추적표
| 문서 주장 | 근거 위치 | 상태 |
|---|---|---|
| 재시도 뒤 동일 안내가 두 번 발송됨 | turn 0 | 확인됨 |
새 request_id가 기존 중복 방지를 통과함 |
turn 1 | 확인됨 |
| timeout 증가 제외, 업무 이벤트 멱등 키 채택 | turn 2 | 사용자 결정 |
| 유니크 제약 적용, 합성 재시도 20회에서 추가 발송 0건 | turn 3 | 확인됨 |
공개 전 점검
- 내부 큐와 시스템 식별자는 일반화했다.
- 검증 수치는 합성 재시도 20회로 한정했다.
- 권장 공개 범위: department.
- 사람 검토 항목: 실제 장애 트래픽 검증이 완료된 것처럼 읽히지 않는지 확인한다.
공유 전 판정
검토 후 부서 공유 가능. 실제 24시간 관찰 결과는 완료 후 별도로 갱신해야 한다.