Files
hanarang-dashboard/.qa/SPRINT-006-review-1.md

2.2 KiB

SPRINT-006 QA Review — Iteration 1

  • 검증일시: 2026-04-04 15:10 KST
  • 검증자: 다랑이 (Evaluator)
  • 결과: FAILED (blocking 5건)

검증 항목

항목 결과
npm install
prisma generate
npm test (backend) 26/26 pass
npm run build (backend)
npm run build (frontend) 16 routes

🔴 Blocking 이슈

B1: JWT_SECRET fallback 'changeme' — 3곳 (Critical)

  • 파일: auth.service.ts:85, auth.module.ts:22, events.gateway.ts:48
  • 문제: JWT_SECRET 미설정 시 'changeme'로 토큰 서명 → 공격자가 유효한 JWT 위조 가능
  • 모순: jwt.strategy.ts는 throw하는데 나머지는 fallback → 불일치
  • 수정: 3곳 모두 ?? 'changeme' 제거, ConfigService.getOrThrow 또는 throw 처리

B2: User.role 기본값 "admin" (Critical)

  • 파일: prisma/schema.prisma
  • 문제: 모든 가입자 자동 admin → 초대코드만 알면 SSH restart, 하네스 수정 등 전체 인프라 제어
  • 수정: @default("viewer") + admin 승격 별도 로직 + AdminController에 RoleGuard 추가

B3: WebSocket JWT 실패 시 disconnect 안 함

  • 파일: events.gateway.ts:52-53
  • 문제: invalid token 시 연결 유지 → 미인증 실시간 데이터 수신
  • 수정: catch 블록에서 client.disconnect() 호출

B4: throw new Error → HttpException

  • 파일: auth.controller.ts:32
  • 문제: refresh token 없을 때 throw new Error → 500 반환
  • 수정: throw new BadRequestException('Refresh token required')

B5: register 엔드포인트 rate limit 없음

  • 파일: auth.controller.ts:18-20
  • 문제: 초대코드 brute-force 가능
  • 수정: @UseGuards(ThrottlerGuard) @Throttle({ default: { limit: 3, ttl: 60000 } }) 추가

Non-blocking 이슈 (7건)

  • N1: refresh token localStorage 평문 (httpOnly cookie 전환 권장)
  • N2: AuthProvider 토큰 만료 시 자동 refresh 안 함
  • N3: register에서 refreshToken 미저장
  • N4: login 후 userId: 0 하드코딩
  • N5: DTO 서비스 파일 내 정의 (별도 파일 권장)
  • N6: adminFetch 주석-코드 불일치
  • N7: refresh secret suffix 방식 → 별도 env 권장