발행 전용 연결의 idle heartbeat 사망 후 첫 발행 유실 결함 제거. - REQ-091 발행 재시도 + 강제 재연결(_force_reconnect, is_open 불신) - REQ-092 idle keepalive(execution-loop 단일스레드 틱, process_data_events time_limit=0) - REQ-093 DLQ 가시성 + emit 실패 ERROR 경보(구조화 로그, dcy-029 재사용) - REQ-094 baseline 문서 정합(runtime-flows/operations/project-structure) 독립 opus QC PASS-WITH-NOTES → 시정 2건(ruff F401, AC-3 프로덕션 경로) 완료. 554 passed/47 skipped/회귀 0/ruff clean. NFR-1 wire 무회귀(interface-contract diff 0). BAT-047 release-candidate, REQ-091~094 Implemented. dcy-031. M2 트랙B. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01VHtM5Ws1HKCKQ4JGi6GRb5
6.5 KiB
6.5 KiB
req-092: 발행 전용 연결 idle keepalive (서버 측 heartbeat 사망 예방)
- Status: Implemented
- Type: Exception
- Priority: High
- Owner: project maintainers
Intent
- 발행 전용 RabbitMQ 연결은 consumer 루프(
process_data_events0.2s 틱)와 달리 publish 사이에 I/O가 전혀 없어heartbeat=30설정에도 불구하고 ~60초 idle 후 서버가 연결을 종료한다. keepalive로 idle 구간에도 heartbeat I/O가 나가도록 해 서버 측 연결 종료를 사전 예방하고, REQ-091 재시도 경로를 보완하는 2차 방어선을 구성한다.
Requirement
- 발행 전용 연결에 idle keepalive를 도입해, heartbeat 주기(
heartbeat=30) 내에process_data_events가 최소 1회 이상 호출되도록 보장한다. - keepalive는 pika
BlockingConnection의 스레드 안전성 제약을 위반하지 않는다. 즉, 발행 전용 연결을 소유한 스레드에서만 keepalive I/O를 실행한다. - keepalive의 구체 구현 방식(별도 keepalive 스레드 vs. execution-loop 틱에 삽입)은 draft-batch-design에서 OQ-1 기준으로 확정한다. 본 REQ는 "발행 연결 소유 스레드 내 I/O 보장" 정책만 확정하며, 구현 위치는 설계 단계 결정으로 추적한다.
- 이 변경은
adapters/messaging/rabbitmq.py및 필요 최소 범위의runtime/daemon.py에 국소화하며, consume/RPC 경로·슬롯 도메인·broker 집행 로직을 건드리지 않는다(NFR-3 흡수). - M1 운영 배포본(
9e35467)의 wire 계약은 불변이다(NFR-1 흡수).
Acceptance Criteria
- Given idle 구간이
heartbeat × 2(60초) 이상 지속될 때, When keepalive가 활성화되어 있으면, Then 발행 전용 연결이 서버에 의해 종료되지 않고 살아 있는 상태를 유지한다(S-1 1차 방어선). - Given keepalive 구현이 별도 스레드를 사용하거나 루프 틱에 삽입되는 경우, When 해당 I/O가 실행될 때, Then 발행 전용 연결을 소유한 스레드에서만
process_data_events가 호출되며, 다른 스레드가 동일 연결에 직접 I/O를 호출하지 않는다(pika 스레드 안전성 불변식). - Given keepalive가 동작 중이고 동시에 발행이 발생할 때, When 두 작업이 겹치면, Then 연결 상태 손상 또는 예외 없이 정상 완료된다(pika 스레드 안전성 불변식 보강).
- Given keepalive 설정이 적용된 상태에서, When execution-loop의 매도 트리거 처리 타이밍을 확인하면, Then keepalive 틱이 execution-loop를 과도하게 블록하지 않는다(NFR-2 흡수 — 허용 블록 시간 상한은 design 단계 확정).
- Given consumer 스레드(intent/slots/control RPC)를 확인할 때, When keepalive 변경이 적용된 코드베이스를 검사하면, Then consumer 경로의 동작·큐 바인딩·토폴로지에 변화가 없다(consume/RPC 무회귀, NFR-1).
- Given keepalive 구현 방식이 설계 단계에서 확정된 후, When batch design 문서를 확인하면, Then OQ-1(keepalive 실행 위치·스레드 소유 모델)이 명시적으로 결정되어 있다(OQ-1 종료 조건 추적).
Impacted Area
- Docs: docs/runtime-flows.md(
데몬 lifecycle흐름 — keepalive 틱 추가 기재, REQ-094에서 갱신). docs/project-structure.md(keepalive 컴포넌트 추가 시 반영, REQ-094에서 갱신). - Modules:
trex_core/adapters/messaging/rabbitmq.py(keepalive 메커니즘 추가).trex_core/runtime/daemon.py(keepalive 연동, 최소 변경). 슬롯 도메인/broker 집행/consume 경로 불변. - Tests:
tests/adapters/messaging/— idle 60초 후 연결 생존 확인(AC-1), 스레드 소유 검증(AC-2), 동시 발행+keepalive 충돌 없음(AC-3), execution-loop 블록 상한(AC-4), consume 경로 회귀(AC-5).
Notes
- 출처: dcy-031 FR-2(A), NFR-1, NFR-2, NFR-3, R-2(keepalive pika 스레드 충돌), S-1.
- OQ-1(keepalive 구현 위치 — 별도 스레드 vs. execution-loop 삽입): 설계 단계 결정. AC-6에서 추적. 종료 조건: batch design 문서에 명시되면 Answered.
- R-2(pika 스레드 비안전성): 이 위험은 AC-2/AC-3으로 검증하며, 설계 단계(OQ-1)에서 구현 방식을 확정해 완화한다.
- keepalive는 REQ-091 재시도와 독립 계층이다. keepalive는 1차 예방(연결 사망 방지), REQ-091은 2차 복구(사망 후 재연결+재시도). 두 REQ는 함께 배치될 예정이지만 독립 구현·독립 검증 가능하다.
Change Log
CHG-20260619-01
- Date: 2026-06-19
- Author: trex-core-dev
Change Summary
- dcy-031 FR-2(A) 로부터 최초 생성(Proposed). NFR-1·NFR-2·NFR-3 흡수. R-2(pika 스레드) OQ-1 인계. S-1 연결.
Intent
- 발행 전용 연결 idle keepalive 정책을 backlog에 정규화하고, OQ-1 설계 결정 추적을 AC-6으로 고정한다.
Acceptance Criteria Delta
- Added:
- AC-1: idle 60초 후 연결 생존
- AC-2: 발행 소유 스레드에서만 I/O (스레드 안전성)
- AC-3: 동시 발행+keepalive 충돌 없음
- AC-4: execution-loop 블록 상한
- AC-5: consume/RPC 경로 무회귀
- AC-6: OQ-1 종료 조건 추적
- Updated: 없음
- Removed: 없음
Impacted Area Delta
- Docs:
- docs/runtime-flows.md, docs/project-structure.md
- Modules:
- trex_core/adapters/messaging/rabbitmq.py, trex_core/runtime/daemon.py
- Tests:
- tests/adapters/messaging/ (idle/스레드/동시성/블록/회귀)
Delivery Trace Delta
- Batches:
- none (draft-req 단계, batch 미편성)
- Releases:
- none
Revalidation Impact
- Reverification Needed: no
- Existing Implementation Invalidated: no
- Status Recommendation: keep-current
- Follow-up Action: confirm-req 후 REQ-091과 함께 단일 batch 편성 예정
Validation Plan
- time-freeze 또는 sleep mock으로 idle 구간을 시뮬레이션한 후 연결 생존 + 스레드 안전성 검증. 기존 messaging 회귀 스위트 전체 통과 확인.
CHG-20260619-02
- Date: 2026-06-19
- Author: 팀장 (confirm-req)
Change Summary
- Proposed → Approved. 필수 필드 충족, AC 구체, source dcy-031(confirmed, Open OQ 0) 정합. OQ-1(keepalive 실행 위치)은 AC-6에서 design 인계 추적 — 승인 비차단.
Intent
- delivery input 승인. keepalive 구현 위치(별도 스레드 vs execution-loop 틱)는 draft-batch-design에서 확정.
Acceptance Criteria Delta
- Added: 없음
- Updated: 없음
- Removed: 없음
Revalidation Impact
- Reverification Needed: no
- Existing Implementation Invalidated: no
- Status Recommendation: keep-current
- Follow-up Action: REQ-091과 함께 단일 batch 편성 예정