docs: SEC-02·03·04 구현 완료 표기 + CI 의존성 스캔 문서화
- 티켓 풀: 감사로그(SEC-02)·레이트리밋(SEC-03)·접근로그(SEC-04) '구현됨' 표기 - CI.md: npm audit·OSV-Scanner(비차단) 구성과 Spring Boot 3.4.2 누적 CVE 발견 기록 Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
This commit is contained in:
parent
e04e93cf18
commit
a5deecf519
17
deploy/CI.md
17
deploy/CI.md
@ -83,6 +83,23 @@ CI가 통과해야 하는 관문이 아래처럼 늘었다. **로컬에서 먼
|
||||
> 커버리지 바닥(30%/40%)은 "지금보다 나빠지지 마라"는 **래칫(ratchet)**이다.
|
||||
> 테스트를 늘리면 이 숫자도 함께 올려 바닥을 끌어올리는 게 건강한 흐름.
|
||||
|
||||
## 의존성 취약점 스캔 (라이브러리 CVE)
|
||||
|
||||
우리가 직접 쓴 코드뿐 아니라 "가져다 쓰는 라이브러리"에도 취약점이 생긴다. CI가 이를 훑는다.
|
||||
|
||||
| 대상 | 도구 | 방식 |
|
||||
|---|---|---|
|
||||
| 프론트(npm) | `npm audit --omit=dev --audit-level=high` | 온디맨드(대용량 DB 없음) |
|
||||
| 백엔드(Maven) | OSV-Scanner v2.4.0, `scan source -r backend` | osv.dev 온디맨드 질의 |
|
||||
|
||||
**둘 다 비차단(`continue-on-error`)으로 "보고 전용" 시작한다.** 이유: 이 스캔은 "코드"가
|
||||
아니라 "외부 권고 DB 상태"에 결합돼, 우리가 한 줄도 안 고쳐도 새 CVE가 공개되면 차단형이면
|
||||
무관한 PR까지 전부 CI가 붉어진다. 팀이 수용목록(allow-list) 운영에 익숙해지면 차단으로 승격한다.
|
||||
|
||||
> ⚠️ **첫 스캔이 이미 값어치를 증명했다**: 백엔드 OSV 스캔이 Spring Boot 3.4.2의
|
||||
> 누적 CVE(tomcat-embed-core·spring-security-* 등, 일부 CVSS 9점대)를 다수 찾아냈다.
|
||||
> 대부분 **Spring Boot 패치 버전 업그레이드로 한 번에 해결**된다 — 별도 후속 티켓 권장.
|
||||
|
||||
## main 브랜치 보호 (PR 워크플로)
|
||||
|
||||
`main`은 보호 규칙이 걸려 있다(Gitea → 저장소 설정 → 브랜치):
|
||||
|
||||
@ -438,7 +438,7 @@
|
||||
</div>
|
||||
|
||||
<div class="ticket">
|
||||
<div class="tk-head"><div><div class="id">SEC-02</div><h3>민감 PII 작업 감사로그</h3></div><div class="tk-meta"><span class="diff d1">★</span><span class="dur">1일</span></div></div>
|
||||
<div class="tk-head"><div><div class="id">SEC-02</div><h3>민감 PII 작업 감사로그 <span style="color:var(--teal)">✅ 구현됨</span></h3></div><div class="tk-meta"><span class="diff d1">★</span><span class="dur">1일</span></div></div>
|
||||
<div class="tk-body">
|
||||
<div class="row what"><span class="lab">무엇을</span><span class="txt">전체 인적사항 CSV 다운로드·멘토 비번 재설정·명단 조회에 "행위자(멘토)+대상 학생 id+시각"을 <code>log.info</code>로 남긴다. 세션 Authentication에서 행위자를 얻는다.</span></div>
|
||||
<div class="row find"><span class="lab">찾는 법</span><span class="txt">백엔드 log.* 호출은 LoginAttemptService·TelegramNotifier뿐. mentor/auth/profile 경로엔 감사로그가 전무 — 누가 전체 명단을 받았는지 추적 불가.</span></div>
|
||||
@ -448,7 +448,7 @@
|
||||
</div>
|
||||
|
||||
<div class="ticket">
|
||||
<div class="tk-head"><div><div class="id">SEC-03</div><h3>공개 쓰기 엔드포인트 레이트리밋</h3></div><div class="tk-meta"><span class="diff d2">★★</span><span class="dur">2일</span></div></div>
|
||||
<div class="tk-head"><div><div class="id">SEC-03</div><h3>공개 쓰기 엔드포인트 레이트리밋 <span style="color:var(--teal)">✅ 구현됨</span></h3></div><div class="tk-meta"><span class="diff d2">★★</span><span class="dur">2일</span></div></div>
|
||||
<div class="tk-body">
|
||||
<div class="row what"><span class="lab">무엇을</span><span class="txt">이미 있는 LoginAttemptService 패턴(IP+창시간)을 재사용해 <code>POST /api/auth/signup</code>과 <code>PUT /api/profile/me</code>에 분당 상한을 건다.</span></div>
|
||||
<div class="row find"><span class="lab">찾는 법</span><span class="txt">signup은 무인증으로 DB에 계정을 쓰고 성공마다 텔레그램 알림까지 쏜다 — 남용 시 가짜계정·알림 폭주 표면.</span></div>
|
||||
@ -458,7 +458,7 @@
|
||||
</div>
|
||||
|
||||
<div class="ticket">
|
||||
<div class="tk-head"><div><div class="id">SEC-04</div><h3>개인정보 열람·내보내기 접근 로그</h3></div><div class="tk-meta"><span class="diff d1">★</span><span class="dur">0.5일</span></div></div>
|
||||
<div class="tk-head"><div><div class="id">SEC-04</div><h3>개인정보 열람·내보내기 접근 로그 <span style="color:var(--teal)">✅ 구현됨 (SEC-02에 통합)</span></h3></div><div class="tk-meta"><span class="diff d1">★</span><span class="dur">0.5일</span></div></div>
|
||||
<div class="tk-body">
|
||||
<div class="row what"><span class="lab">무엇을</span><span class="txt"><code>/api/mentor/students</code>(전체 인적사항)와 <code>/export.csv</code>에 접근 한 줄(사용자·행위·시각) 로그를 남긴다. SEC-02와 짝.</span></div>
|
||||
<div class="row find"><span class="lab">찾는 법</span><span class="txt">두 경로 모두 누가·언제 접근했는지 기록이 0. 유출 시 추적 근거가 없다.</span></div>
|
||||
|
||||
Loading…
x
Reference in New Issue
Block a user