feat(creator): 내 채널 팔로워 목록을 연결한다

This commit is contained in:
2026-08-03 21:39:23 +09:00
parent e86e5a1c3d
commit f508d847ea
5 changed files with 466 additions and 0 deletions

View File

@@ -0,0 +1,213 @@
# 내 채널 팔로워 목록 연결 Implementation Plan
> **For agentic workers:** REQUIRED SUB-SKILL: Use superpowers:test-driven-development to implement this plan task-by-task. Steps use checkbox (`- [ ]`) syntax for tracking.
**Goal:** 내 채널 상단 `팔로워 n명` 터치 시 기존 레거시 팔로워 목록 화면으로 이동한다.
**Architecture:** `CreatorChannelActivity`가 이미 헤더와 현재 `creatorId`를 소유하므로 Activity 내부에서 클릭 리스너를 추가한다. 목적지는 레거시 `UserFollowerListActivity`이며 기존 호출 방식처럼 `Constants.EXTRA_USER_ID`만 전달한다.
**Tech Stack:** Android Kotlin, ViewBinding, JUnit source test, Gradle `:app:testDebugUnitTest`, `:app:assembleDebug`.
---
| 문서 항목 | 내용 |
|---|---|
| 상태 | 구현 완료 |
| 작성일 | `2026-08-03` |
| 요구사항 기준 | `docs/20260803_내_채널_팔로워_목록_연결/prd.md` |
| API 기준 | 기존 레거시 `UserFollowerListActivity` / `ExplorerApi.getFollowerList` |
| 현재 Phase | Phase 1 |
| 현재 활성 Goal | 없음 |
## 목표
내 채널 소유자가 v2 크리에이터 채널의 `팔로워 n명`을 눌러 기존 레거시 팔로워 목록을 확인한다.
## 현재 상태
| Phase | 상태 | 완료 Task | 활성/다음 Goal | 차단 또는 남은 조건 |
|---:|---|---:|---|---|
| 1 | 완료 | `1/1` | 없음 | 직접 Activity 기동은 `not exported` 보안 정책상 adb에서 차단됨 |
## 범위
### 포함
- `CreatorChannelActivity``tvFollowerCount` 클릭 연결.
- 기존 `UserFollowerListActivity``Constants.EXTRA_USER_ID = creatorId` 전달.
- owner 전용 동작과 0명 허용 계약을 source test로 고정.
### 제외
- 신규 v2 팔로워/팔로잉 목록 화면.
- 레거시 `UserFollowerListActivity` 및 API 수정.
- 타인 채널의 팔로워 수 클릭 동작.
- 팔로워/팔로잉 문구 변경.
## 기술적 제약
- 레거시 코드는 직접 수정하지 않는다.
- 새 dependency, router, helper abstraction을 추가하지 않는다.
- 기존 `CreatorChannelActivitySourceTest`의 source-test 패턴을 따른다.
- production 구현은 RED 확인 후 진행한다.
## Phase 1
**Phase 결과:** 내 채널 헤더의 `팔로워 n명`이 레거시 팔로워 목록으로 이동한다.
**선행조건:** PRD 승인 완료.
**Phase 완료 조건:** `P1-T1``P1-GATE` 완료, 검증 기록 누적.
### 구현 항목
#### Task 1.1 내 채널 팔로워 수 클릭 연결
**Goal 실행 `P1-T1`:** `CreatorChannelActivity`에서 owner의 `tvFollowerCount` 클릭을 `UserFollowerListActivity`로 연결한다.
- **시작 조건:** `FOLLOWER-LINK-001~003` 확정.
- **완료 증거:** RED/GREEN source test, debug build, 수동 검증 기록.
- **범위 밖:** 레거시 화면 수정, 신규 v2 화면 작성, 타인 채널 동작 추가.
**Files:**
- Modify: `app/src/test/java/kr/co/vividnext/sodalive/v2/creator/channel/CreatorChannelActivitySourceTest.kt`
- Modify: `app/src/main/java/kr/co/vividnext/sodalive/v2/creator/channel/CreatorChannelActivity.kt`
**Interfaces:**
- Consumes: `creatorId: Long`, `currentHeader?.isOwner`, `Constants.EXTRA_USER_ID`.
- Produces: `Intent(this, UserFollowerListActivity::class.java).putExtra(Constants.EXTRA_USER_ID, creatorId)` 실행 경로.
- [x] **RED:** `CreatorChannelActivitySourceTest``내 채널 팔로워 수 클릭 source는 레거시 팔로워 목록으로 이동한다` 테스트를 추가한다.
```kotlin
@Test
fun `내 채널 팔로워 수 클릭 source는 레거시 팔로워 목록으로 이동한다`() {
val source = projectFile(
"app/src/main/java/kr/co/vividnext/sodalive/v2/creator/channel/CreatorChannelActivity.kt"
).readText()
val clickSource = sourceSection(
source = source,
startMarker = "private fun onFollowerCountClicked()",
endMarker = "private fun bindHeader"
)
assertTrue(source.contains("import kr.co.vividnext.sodalive.explorer.profile.follow.UserFollowerListActivity"))
assertTrue(source.contains("binding.tvFollowerCount.setOnClickListener"))
assertTrue(clickSource.contains("if (currentHeader?.isOwner != true) return"))
assertTrue(clickSource.contains("Intent(this, UserFollowerListActivity::class.java)"))
assertTrue(clickSource.contains("putExtra(Constants.EXTRA_USER_ID, creatorId)"))
assertFalse(clickSource.contains("followerCount > 0"))
assertFalse(source.contains("FollowingCreatorActivity::class.java"))
}
```
- [x] **RED 확인:** focused test를 실행해 `start marker not found: private fun onFollowerCountClicked()` 실패를 확인한다.
```bash
./gradlew :app:testDebugUnitTest --tests "kr.co.vividnext.sodalive.v2.creator.channel.CreatorChannelActivitySourceTest.내 채널 팔로워 수 클릭 source는 레거시 팔로워 목록으로 이동한다"
```
- [x] **GREEN:** `CreatorChannelActivity`에 import, click listener, 최소 handler를 추가한다.
```kotlin
import kr.co.vividnext.sodalive.explorer.profile.follow.UserFollowerListActivity
binding.tvFollowerCount.setOnClickListener { onFollowerCountClicked() }
private fun onFollowerCountClicked() {
if (currentHeader?.isOwner != true) return
startActivity(
Intent(this, UserFollowerListActivity::class.java)
.putExtra(Constants.EXTRA_USER_ID, creatorId)
)
}
```
- [x] **GREEN 확인:** 같은 focused test가 성공하는지 확인한다.
```bash
./gradlew :app:testDebugUnitTest --tests "kr.co.vividnext.sodalive.v2.creator.channel.CreatorChannelActivitySourceTest.내 채널 팔로워 수 클릭 source는 레거시 팔로워 목록으로 이동한다"
```
- [x] **REFACTOR:** 불필요한 변경이 없는지 확인하고 아래 직접 영향 회귀를 실행한다.
```bash
./gradlew :app:testDebugUnitTest --tests "kr.co.vividnext.sodalive.v2.creator.channel.CreatorChannelActivitySourceTest"
./gradlew :app:assembleDebug
```
### 검증 방법
#### Phase 1 Gate
**Goal 실행 `P1-GATE`:** 문서와 코드가 요구사항을 충족하는지 최종 판정한다.
```bash
./gradlew :app:testDebugUnitTest --tests "kr.co.vividnext.sodalive.v2.creator.channel.CreatorChannelActivitySourceTest"
./gradlew :app:assembleDebug
```
**Expected:** test/build 모두 exit code 0. `CreatorChannelActivity``UserFollowerListActivity`만 참조하고 `FollowingCreatorActivity`를 참조하지 않는다.
수동 검증:
- [ ] Android 실행 환경에서 내 채널 진입 후 `팔로워 n명` 터치 시 `UserFollowerListActivity`가 열리는지 확인한다.
- [x] 실행 환경이 없으면 사용 가능한 명령과 부재 사유를 Progress에 기록한다.
## 실행 순서와 의존성
| 순서 | Goal | 선행조건 | 병행 가능 | 차단 시 다음 행동 |
|---:|---|---|---|---|
| 1 | `P1-T1` | PRD 승인 | 아니요 | 테스트 실패 원인을 해당 Task에서 수정 |
| 2 | `P1-GATE` | `P1-T1` 완료 | 아니요 | 실패 소유 Task에 회귀 수정 기록 추가 |
```text
P1-T1 -> P1-GATE
```
## 변경 금지 항목
- 레거시 `UserFollowerListActivity`를 수정하지 않는다.
- 새 화면, dependency, router abstraction을 만들지 않는다.
- test를 삭제, skip, 완화하지 않는다.
- 민감정보를 로그, Toast, 문서에 기록하지 않는다.
## Progress
기존 기록을 삭제하거나 덮어쓰지 않고 실제 실행 결과를 누적한다.
### P1-T1 1차 실행 — 2026-08-03
- 상태: 완료
- 무엇을: `CreatorChannelActivity``tvFollowerCount` 클릭을 owner 전용 `UserFollowerListActivity` 진입으로 연결하고 source test를 추가했다.
- 왜: `FOLLOWER-LINK-001~003` 구현 기준 충족.
- 어떻게:
- `./gradlew :app:testDebugUnitTest --tests "kr.co.vividnext.sodalive.v2.creator.channel.CreatorChannelActivitySourceTest.내 채널 팔로워 수 클릭 source는 레거시 팔로워 목록으로 이동한다"` — RED 실패, `CreatorChannelActivitySourceTest.kt:2378`에서 `onFollowerCountClicked()` source marker 부재로 실패.
- 같은 focused 명령 재실행 — GREEN 성공, exit code 0.
- `./gradlew :app:testDebugUnitTest --tests "kr.co.vividnext.sodalive.v2.creator.channel.CreatorChannelActivitySourceTest"` — 성공, exit code 0.
- `./gradlew :app:testDebugUnitTest` — 성공, exit code 0.
- `./gradlew :app:assembleDebug` — 성공, exit code 0.
- `adb install -r "app/build/outputs/apk/debug/app-debug.apk"` — 성공.
- `adb shell am start -W -n kr.co.vividnext.sodalive.debug/kr.co.vividnext.sodalive.explorer.profile.follow.UserFollowerListActivity --el extra_user_id 1``not exported` 보안 정책으로 직접 Activity 기동 차단.
- `adb shell monkey -p kr.co.vividnext.sodalive.debug 1` — debug 앱 실행 이벤트 주입 성공.
- 남은 항목: 로그인된 내 채널 실제 클릭 검증은 인증 상태가 있는 수동 QA 환경에서 확인 필요.
- 다음 행동: 없음.
## Decision Log
| 날짜 | ID | 상태 | 결정 | 근거 | 영향 Goal/문서 |
|---|---|---|---|---|---|
| `2026-08-03` | `DEC-001` | 확정 | `UserFollowerListActivity`를 목적지로 사용한다. | 내 채널을 팔로우하는 사용자 목록 요구. | `P1-T1`, `prd.md#15-decision-log` |
## 발견된 문제
| ID | 심각도 | 상태 | 발견 내용 | 영향 Goal | 처리 계획 |
|---|---|---|---|---|---|
| 없음 | Low | 보류 | 현재 발견된 범위 내 문제 없음 | 없음 | 없음 |
## Verification Log
- `2026-08-03`: RED/GREEN source test, 직접 영향 source test, 전체 debug unit test, debug build가 모두 성공했다. 연결된 Android 기기에는 APK 설치와 앱 실행 이벤트 주입까지 확인했으나, 레거시 Activity 직접 기동은 `not exported` 보안 정책으로 차단되어 로그인된 내 채널에서의 실제 클릭은 별도 QA 환경에서 확인해야 한다.
- `2026-08-03`: 리뷰 게이트를 수행했고 `reviews/phase1-follower-list-link-review.md`에 확정 발견 사항 없음으로 기록했다.