---
title: "[WS-J] 하드닝 스윕 완료 — PR #10 (백145/프론트79/Go/build OK)"
from: claude-code
to: ["jadong"]
project: "callcenter-os"
date: 2026-07-05T23:44:46.467975+09:00
status: sent
type: report
---

# [WS-J] 하드닝 스윕 완료 — callcenter-os PR #10

병렬 2차 라운드 WS-J. M2·M3 최종 리뷰가 이연시킨 보안·견고성 10항목을 **항목별 개별 커밋 + 테스트**로 일괄 처리.

## 결과
- **PR**: https://github.com/shinjadong/callcenter-os/pull/10 (11커밋 = 10항목 + STATUS)
- **회귀**: 백엔드 pytest **145**(baseline 134 +11) · 프론트 vitest **79**(75 +4) · go test OK · cockpit build OK
- **브랜치**: `feat/ws-j-hardening` (전용 worktree 격리, base origin/main 202a9d9)

## 10항목
1. recordings 페이지네이션(limit/offset) + 업로드 25MB 상한(413)
2. /리드 slash 평문전화 마스킹 — 코어 `?masked=1` + mm-plugin Go(masked=1 조회)
3. WS 인증 사용자 실존 확인(`s.get(User,uid)`) — 삭제/타테넌트 토큰 4401 차단
4. realtime 4403 재접속 중단(로그아웃 아님, 콘솔 에러만)
5. device_or_user 비ASCII 헤더 500→401 (hmac.compare_digest bytes 비교)
6. ingest len(items) 1,000 초과 413 (calls·messages)
7. README M3 교정: whisper 전사+Qwen(Ollama) 분석 / 타임라인 `at`·`ref_id` 실스키마
8. quote-engine vendor 출처 박제(원본 SHA `43826b3`, 8개 .ts byte-identical) + KT 단가검증=자동님 몫 명시
9. Qa onSave try/catch 한국어 에러(unhandled rejection 제거)
10. GRADE_COLOR(null) 중립색(danger 빨강 → --ink-soft)

## 동결 해제 범위 준수
`ws.py`(#3)·`realtime.ts`(#4)만 PM 사전승인 범위 내 수정. auth.py 인증계약·events.py·api.ts 미접촉. `git add` 파일 명시(스트레이 없음), 빌드 산출물 `core/static/`는 gitignore.

## 다음 액션
PM 머지 큐(우선순위 F > J). PR #10 리뷰·머지 대기. 후속 트래킹 항목(quote-engine A·`/리드` 평문 B) 이번 PR로 해소.
