Skip to content

♻️ week_order 컬럼을 topic_order로 리네임 (V13) - #48

Closed
s26059-maker wants to merge 97 commits into
mainfrom
feat/rename-topic-order
Closed

s26059-maker wants to merge 97 commits into
mainfrom
feat/rename-topic-order

Conversation

@s26059-maker

Copy link
Copy Markdown
Contributor

개요

topic.week_order 컬럼을 topic_order로 리네임합니다. 코드 레벨 리네임(weekOrder → topicOrder)은 이전에 끝났고, 이번 PR에서 DB 컬럼까지 맞춥니다.

변경 사항

  • V13__rename_week_order_to_topic_order.sql 추가
    • ALTER TABLE topic RENAME COLUMN week_order TO topic_order;
  • Topic.java에서 @Column(name = "week_order") 매핑 제거 (기본 네이밍으로 topic_order 매핑)
  • TopicRotationPolicy 주석의 컬럼명 수정
  • 기존 V1~V12는 수정하지 않음 (체크섬 유지)
    • V5__seed_topics.sql 주석에 week_order가 남아 있지만, 체크섬 때문에 그대로 둠

검증

  • ./gradlew test 통과
  • 테스트는 H2 + Flyway off 환경이라 마이그레이션은 로컬 Docker MySQL에서 별도 확인
    • V12 상태 DB에 V13 적용 → ddl-auto: validate 통과 → 정상 기동
    • 시드 8행 유지 확인

⚠️ 머지 순서

feat/submission-history(V14)보다 먼저 머지해야 합니다.
V14가 먼저 들어가면 Flyway가 V13을 순서가 어긋난 마이그레이션으로 판단해 실패합니다.

API 영향

없음 (응답 필드는 이미 topicOrder)

s26059-maker and others added 30 commits July 2, 2026 14:15
- 테스트용 application.yml이 main 설정을 대체하면서 ai.* 블록이 사라져
  AiProperties.exec()가 null → LocalProcessExecutor 생성자 NPE로 contextLoads 실패.
- AiProperties에 기본값 채우는 compact constructor 추가(설정 없어도 데모로 동작).
- 테스트 yml에 ai.executor=demo 명시(테스트에서 프로세스 실행 방지).

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
RestClientException(401/429/5xx/타임아웃)이 그대로 전파되지 않도록
try-catch로 감싸 OpenAiException으로 통일 — 호출부 재시도 처리 일관화.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
1. generate()가 GenerationOutcome 반환 — 조합별 성공/실패 레코드
   (language/difficulty/attempts/failReason, ai_generation_log 1:1 대응).
   한 조합 실패해도 성공분 유실 없음. GenerationFailedException 폐기.
2. 실키 모드 + 툴체인 부재 시 부팅 실패(fail-fast) — 검증이 조용히
   꺼진 채 배포 방지. 데모 폴백은 키 없음/AI_EXECUTOR=demo 명시일 때만.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
1. items.size() != 3이면 예외 — 초과 항목으로 합계가 30.00을 넘어
   백엔드 만점 가정이 깨지는 것 차단.
2. INSTANT_SYSTEM에 방어 문구 추가 — 제출 코드 내 주석/문자열 지시
   (점수 요구 등)를 데이터로만 취급, 항목 3개 고정 명시.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
연결 오류 수정함
GET /api/v1/health - 서버 생존 확인용, 상태 JSON({"status":"UP"}) 반환

Co-Authored-By: Claude Sonnet 5 <noreply@anthropic.com>
헬스체크 엔드포인트 추가
- V1__init.sql: 전체 10개 테이블, FK 제약 명시 (user/rank 예약어 백틱 처리)
- 도메인별 패키지에 엔티티 10개 + enum (ManyToOne LAZY 단방향, setter 없이 의도 메서드)
- User에 JPA Auditing 적용
- datasource 환경변수화 (DB_URL/DB_USERNAME/DB_PASSWORD, 로컬 기본값 3308)
- compose.local.yaml 추가: 로컬 MySQL 8.0 원커맨드 구동
- ddl-auto=validate 전환, spring-boot-starter-flyway 도입 (Boot 4 대응)
✨Flyway V1 마이그레이션 및 JPA 엔티티 10종 추가
✨ DataGSM OAuth 로그인(signin) 구현
- PUT /api/v1/auth/reissue: refresh 검증 + DB 대조 + 토큰 로테이션
- POST /api/v1/auth/signout: refresh_token 무효화 (인증 필요)
- JwtProvider.isRefreshToken, RefreshToken 예외 2종, AuthErrorCode 메시지 통합
✨ JWT 재발급(reissue)·로그아웃(signout) 구현
OpenAiException(타임아웃·429·5xx)이 port를 넘어 백엔드로 새던 문제.
계약(재시도 3회는 모듈 내부, 백엔드는 계약 예외만 캐치)에 맞춰:

- evaluate()에 재시도 루프(생성 경로와 동일 maxRetries) 추가
- 소진 시 InstantFeedbackFailedException(port 패키지)으로 래핑,
  원인 예외는 cause로 보존
- port 인터페이스에 @throws 계약 문서화
- 재시도/래핑 검증 테스트 4건 추가

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
fix(ai): 즉시 피드백 경로 재시도 + 계약 예외 적용
✨ feat: 현재 회차 조회 API 구현
s26059-maker and others added 28 commits July 14, 2026 00:02
Railway 빌더가 --mount=type=cache에 id 인자를 요구해 빌드 실패
(dockerfile invalid: flag '--mount=type=cache,target=/root/.gradle' is missing an id argument).
id=gradle-cache 추가로 해결. 로컬 BuildKit은 원래 id 없이도 통과했던 걸 보면
Railway 쪽 빌더가 더 엄격한 버전으로 보임.

검증: 로컬 docker build 성공, non-root 유저/gcc/python3 정상 동작 재확인.
* feat: Judge0 부재 시 동작하는 StubJudgeService 추가

* fix: 스텁 빈이 Judge0 환경에서도 즉시 생성되던 문제 수정
* feat: Judge0 부재 시 동작하는 StubJudgeService 추가

* fix: 스텁 빈이 Judge0 환경에서도 즉시 생성되던 문제 수정

* 🐛 fix: 로컬 MySQL 포트 3308 → 13306 변경

Windows Hyper-V가 3307-3406 구간을 예약해 3308 바인딩이 실패하는 문제 해결
* ♻️ refactor: 다음 주차 계산식을 nextWeekOrder로 추출

* ✨ feat: 기간별 언어/난이도/오답유형 집계 쿼리 추가

* ✨ feat: PeriodStats 집계 및 PeriodFeedbackProvider 연동

* ♻️ refactor: 주차 순환 규칙을 TopicRotationPolicy로 통합

* ♻️ refactor: enum 변환을 switch 기반 명시적 변환으로 교체
* ♻️ refactor: 다음 주차 계산식을 nextWeekOrder로 추출

* ✨ feat: 기간별 언어/난이도/오답유형 집계 쿼리 추가

* ✨ feat: PeriodStats 집계 및 PeriodFeedbackProvider 연동

* ♻️ refactor: 주차 순환 규칙을 TopicRotationPolicy로 통합

* ♻️ refactor: enum 변환을 switch 기반 명시적 변환으로 교체
* ➕ FeedbackService 유닛 테스트 13개 추가

* 🎨 테스트 timezone 고정 및 주석 정리
* ✨ 기간별 피드백 조회 API 구현

* 🎨 컨트롤러 테스트 주석 정리
* ⚡️ 즉시 피드백 전용 타임아웃/재시도 설정 분리

* ♻️ maxRetries를 maxAttempts로 정정하고 설정값 범위 검증 추가
- JudgeConfig 분리: judge.engine(judge0|runner|stub)으로 구현체 선택
- RunnerJudgeAdapter 추가: X-Runner-Token 인증, 연결/읽기 타임아웃
  - runner MLE는 RE로 변환, 4xx/5xx/타임아웃은 502(JUDGE_EXECUTION_FAILED)
- JudgeService에 run() 추가, POST /api/v1/run 신규
  - 로그인 필요, 유저당 분당 10회 제한, code/stdin 64KB 제한
- 제출(POST /api/v1/submissions)에도 code 64KB 제한(400) 추가
  - InputSizeGuard로 /run과 검사 로직 공용화
- Verdict, DB, AI 입력은 변경 없음
- 사용처 없는 judge0Id 필드/생성자/접근자 삭제
- 언어 → Judge0 ID 매핑은 infra.judge0.LanguageMapper에만 남김
- FeedbackService 주석에서 삭제된 필드 언급 제거
- 재시도 불가 에러(크레딧 소진 429, 401)는 즉시 포기하고 남은 조합도 중단
  - 건너뛴 조합은 실패 항목으로 채워 회차당 로그 9건 유지
- 전체 실패여도 비활성 회차로 저장하고 실패 로그를 남김
  - 같은 날 재트리거 시 빈 비활성 회차 재사용, 이전 로그는 유지
  - skipped 응답에 failureCount 포함
- 빈 실패 회차가 다른 로직에 섞이지 않게 "문제 있는 회차" 기준으로 조회 변경
  - 토픽 로테이션, TopicService 폴백, 랭킹 배치, 회차 피드백
MissingServletRequestParameterException을 GlobalExceptionHandler에서 처리해
Spring 기본 400 대신 {code: INVALID_REQUEST, message} 형식으로 내려준다.
/rankings 파라미터 누락 테스트 추가.

Co-authored-by: Claude Sonnet 5.5 <noreply@anthropic.com>
prod 프로필에서 judge.engine이 stub(미설정 포함)이거나 judge0인데
JUDGE0_URL이 비어 stub으로 폴백되는 경우 앱 기동을 실패시킨다.
local/test 프로필은 기존 stub 기본값을 유지한다.

Co-authored-by: Claude Sonnet 5.5 <noreply@anthropic.com>
- V13 마이그레이션: ALTER TABLE topic RENAME COLUMN week_order TO topic_order
- Topic 엔티티의 @column(name = "week_order") 매핑 제거 (필드명 topicOrder 기본 네이밍 사용)
- 로컬 MySQL에서 V13 적용 및 ddl-auto=validate 통과 확인

Co-Authored-By: Claude Sonnet 5.5 <noreply@anthropic.com>
@s26059-maker
s26059-maker deleted the feat/rename-topic-order branch October 12, 2026 11:32
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants