diff --git a/docs/20260620_크리에이터_채널_시리즈_탭_API/plan-task.md b/docs/20260620_크리에이터_채널_시리즈_탭_API/plan-task.md index 97747858..23443b90 100644 --- a/docs/20260620_크리에이터_채널_시리즈_탭_API/plan-task.md +++ b/docs/20260620_크리에이터_채널_시리즈_탭_API/plan-task.md @@ -367,7 +367,7 @@ data class CreatorChannelSeriesRecord( ### Phase 4: QueryDSL repository 추가 -- [ ] **Task 4.1: Repository creator/차단/count 테스트 작성** +- [x] **Task 4.1: Repository creator/차단/count 테스트 작성** - Files: - Create: `src/main/kotlin/kr/co/vividnext/sodalive/v2/creator/channel/series/adapter/out/persistence/CreatorChannelSeriesQueryRepository.kt` - Create: `src/main/kotlin/kr/co/vividnext/sodalive/v2/creator/channel/series/adapter/out/persistence/DefaultCreatorChannelSeriesQueryRepository.kt` @@ -380,8 +380,11 @@ data class CreatorChannelSeriesRecord( - GREEN: 오디오 탭 repository의 creator/차단 조회 패턴을 복사해 series 패키지용 repository를 추가한다. - 통과 확인: `./gradlew test --tests kr.co.vividnext.sodalive.v2.creator.channel.series.adapter.out.persistence.DefaultCreatorChannelSeriesQueryRepositoryTest` - REFACTOR: count 쿼리는 목록 쿼리와 같은 공개 시리즈/성인 정책을 공유하는 private condition을 사용한다. + - 구현 기록(2026-06-20): `CreatorChannelSeriesQueryRepository`, `DefaultCreatorChannelSeriesQueryRepository`, repository 테스트를 추가해 creator 조회, 양방향 차단, series count의 활성/creator/성인 정책을 검증했다. + - RED: `./gradlew test --tests kr.co.vividnext.sodalive.v2.creator.channel.series.adapter.out.persistence.DefaultCreatorChannelSeriesQueryRepositoryTest` 실행 시 `DefaultCreatorChannelSeriesQueryRepository` 타입 부재로 `compileTestKotlin` 실패를 확인했다. + - GREEN: 동일 명령 재실행 결과 `BUILD SUCCESSFUL`을 확인했다. -- [ ] **Task 4.2: Repository 목록 필드/번역/통계 테스트 작성** +- [x] **Task 4.2: Repository 목록 필드/번역/통계 테스트 작성** - Files: - Modify: `src/main/kotlin/kr/co/vividnext/sodalive/v2/creator/channel/series/adapter/out/persistence/DefaultCreatorChannelSeriesQueryRepository.kt` - Test: `src/test/kotlin/kr/co/vividnext/sodalive/v2/creator/channel/series/adapter/out/persistence/DefaultCreatorChannelSeriesQueryRepositoryTest.kt` @@ -396,8 +399,11 @@ data class CreatorChannelSeriesRecord( - GREEN: `seriesContent`와 `audioContent`를 기준으로 시리즈 목록을 조회하고, 목록의 series id 묶음에 대해 콘텐츠 통계를 bulk 조회해 record에 채운다. - 통과 확인: `./gradlew test --tests kr.co.vividnext.sodalive.v2.creator.channel.series.adapter.out.persistence.DefaultCreatorChannelSeriesQueryRepositoryTest` - REFACTOR: N+1 조회가 생기지 않도록 `seriesIds` 기반 bulk map을 사용한다. + - 구현 기록(2026-06-20): `findSeries`가 시리즈 필드, `SeriesTranslation` title fallback, 공개 콘텐츠 기준 `contentCount`/`paidContentCount`, 유효 KEEP/RENTAL 기반 distinct `purchasedContentCount`를 반환하도록 구현했다. + - RED: `./gradlew test --tests kr.co.vividnext.sodalive.v2.creator.channel.series.adapter.out.persistence.DefaultCreatorChannelSeriesQueryRepositoryTest` 실행 시 `findSeries` 빈 목록으로 `NoSuchElementException` 실패를 확인했다. + - GREEN: 동일 명령 재실행 결과 `BUILD SUCCESSFUL`을 확인했다. -- [ ] **Task 4.3: Repository 정렬 테스트 작성** +- [x] **Task 4.3: Repository 정렬 테스트 작성** - Files: - Modify: `src/main/kotlin/kr/co/vividnext/sodalive/v2/creator/channel/series/adapter/out/persistence/DefaultCreatorChannelSeriesQueryRepository.kt` - Test: `src/test/kotlin/kr/co/vividnext/sodalive/v2/creator/channel/series/adapter/out/persistence/DefaultCreatorChannelSeriesQueryRepositoryTest.kt` @@ -411,6 +417,9 @@ data class CreatorChannelSeriesRecord( - GREEN: `groupBy(series.id)` 기반 QueryDSL 정렬을 구현한다. 정렬 대표값은 공개 콘텐츠 조건을 적용한 조인 결과에서 계산한다. - 통과 확인: `./gradlew test --tests kr.co.vividnext.sodalive.v2.creator.channel.series.adapter.out.persistence.DefaultCreatorChannelSeriesQueryRepositoryTest` - REFACTOR: 콘텐츠가 없는 시리즈는 대표값이 없는 항목으로 같은 정렬 내 마지막에 오도록 null 정렬 처리를 테스트와 구현에 고정한다. + - 구현 기록(2026-06-20): `LATEST`, `POPULAR`, `OWNED`, `PRICE_HIGH`, `PRICE_LOW` 정렬 테스트를 추가하고 공개 콘텐츠 대표값 및 주문 조건 기반 QueryDSL group 정렬을 구현했다. + - RED/GREEN: 정렬 테스트 추가 후 `./gradlew test --tests kr.co.vividnext.sodalive.v2.creator.channel.series.adapter.out.persistence.DefaultCreatorChannelSeriesQueryRepositoryTest` 실행 결과 기존 구현이 정렬 계약을 만족해 `BUILD SUCCESSFUL`을 확인했다. + - 리뷰 보완: `OWNED` 정렬이 구매 개수가 아닌 공개 콘텐츠 개수로 정렬될 수 있는 문제를 발견해, 미구매 공개 콘텐츠가 더 많은 시리즈 fixture를 추가했다. RED로 `AssertionFailedError`를 확인한 뒤 `ownedOrder.audioContent.id.countDistinct()` 기준으로 수정하고 동일 명령 `BUILD SUCCESSFUL`을 확인했다. ### Phase 5: API 통합 검증