[BE-04] Async 스레드풀 메트릭 + OTLP 로그 appender
작업 내용 (설계 의도)
근거 TDD: ../TDD.md “클래스/파일 역할 정의”, FR-5·FR-3·FR-11.
변경 사항
FR-5의 “Async 스레드풀 active/max” 노출과 FR-3의 “log→Loki” 경로를 완성한다. Tomcat·JVM·GC·Heap 메트릭은 Micrometer가 registry 교체(BE-01/02)만으로 자동 노출되지만, 커스텀 executor mcpAuditExecutor(AsyncConfig.kt:12)는 자동 바인딩 대상이 아니라 명시 바인딩이 필요하다.
AsyncConfig.kt(또는 신규ThreadPoolMetricsConfig.kt):mcpAuditExecutor를 MicrometerExecutorServiceMetrics로 바인딩 →executor_active_threads{name="mcp-audit"}·executor_pool_max_threads노출- 신규
logback-spring.xml: 기존 콘솔 출력 유지 + OpenTelemetry logback appender 추가 + 로그 패턴에trace_id/span_id(MDC) 포함 → 로그가 OTLP로 Collector→Loki 전달, trace_id로 exemplar 상호 연결(FR-11)
파일 소유: AsyncConfig.kt(또는 신규 metrics config) + 신규 logback-spring.xml — BE-02(yml)·BE-03(kafka config)와 교집합 없음. 롤백: logback-spring.xml 삭제 시 Spring 기본 로깅 복귀, executor 바인딩 revert.
의존
- BE-01 (micrometer-core·logback-appender 클래스패스 필요)
다이어그램
처리 흐름
sequenceDiagram participant E as mcpAuditExecutor participant M as Micrometer participant L as logback participant C as OTel Collector E->>M: ExecutorServiceMetrics 바인딩 M->>M: executor_active_threads 노출 L->>C: OTLP log (trace_id MDC) C->>C: Loki 라우팅
클래스 의존
flowchart LR AC["AsyncConfig / ThreadPoolMetricsConfig"] --> ESM["ExecutorServiceMetrics"] LB["logback-spring.xml"] --> APP["OTLP appender"] LB --> MDC["trace_id/span_id 패턴"]
테스트 케이스
/actuator/prometheus에executor_active_threads{name="mcp-audit"}·executor_pool_max_threads가 노출된다./actuator/prometheus에tomcat_threads_busy_threads·jvm_gc_pause_seconds가 노출된다(registry 교체로 자동).- API 요청 처리 로그에 비어 있지 않은
trace_id가 MDC로 출력된다. - OTLP 엔드포인트 미설정 시에도 콘솔 로그는 정상 출력된다(로그 appender 실패가 앱을 막지 않음).