<!-- task=plane_foundation/02+01_plane_smoke plan=1 tag=REVIEW_PLANE -->

# Plane Real Smoke Follow-up Plan

## 이 파일을 읽는 구현 에이전트에게

`CODE_REVIEW-*-G??.md`의 구현 에이전트 소유 섹션을 채우는 것이 필수입니다. 구현 후 검증 명령을 실행하고 실제 출력과 구현 메모를 review stub에 기록한 뒤 active 파일을 유지한 채 리뷰 준비 상태로 보고하세요. 최종 판정, log rename, `complete.log`, archive 이동은 code-review skill 전용입니다.

## 배경

`code_review_cloud_G07_0.log`의 1차 리뷰는 smoke command와 unit test 자체는 통과했지만, 실제 dev Plane에 대한 lookup/comment/state update smoke가 `PLANE_TOKEN` 부재로 실행되지 않아 FAIL 처리되었습니다. 원 계획은 `PLANE_TOKEN` 또는 test work item이 없으면 완료 처리하지 말라고 했으므로, 이번 후속 작업은 실제 smoke 증거를 확보하는 데만 집중합니다.

## 분석 결과

### 읽을 파일

- `agent-ops/rules/project/domain/core/rules.md`
- `agent-ops/rules/project/domain/workspace-ops/rules.md`
- `agent-task/plane_foundation/02+01_plane_smoke/code_review_cloud_G07_0.log`
- `agent-task/plane_foundation/02+01_plane_smoke/plan_cloud_G07_0.log`
- `services/core/cmd/plane-smoke/main.go`
- `services/core/cmd/plane-smoke/main_test.go`
- `services/core/internal/adapters/plane/client.go`
- `services/core/internal/adapters/plane/client_test.go`
- `services/core/README.md`
- `agent-ops/roadmap/milestones/plane-thin-e2e-loop.md`

### 테스트 커버리지 공백

- mock/unit 검증은 통과했지만 실제 Plane API의 인증 성공, comment 생성, state update 성공 증거가 없다.
- `PLANE_TOKEN=not_set` 상태에서는 이 작업을 완료할 수 없다.

### 범위 결정 근거

- token 생성/보관/교체 운영법은 범위 제외다. token 값은 파일, stdout/stderr 기록, 로그에 남기지 않는다.
- 실제 smoke가 성공하기 전에는 roadmap의 실제 smoke 체크박스를 체크하지 않는다.
- 실제 smoke 실패가 command/adapter의 endpoint, body, redaction 문제를 드러내면 그 최소 범위만 수정하고 테스트를 보강한다.
- Plane 자동 pipeline, webhook, task 완료/실패 자동 발행 정책은 계속 범위 제외다.

### 빌드 등급

build=`cloud-G07`, review=`cloud-G07`. 실제 외부 API와 write mutation 증거가 완료 조건이며, command stdout/stderr와 secret redaction 확인이 필요하다.

## 구현 체크리스트

- [x] 유효한 `PLANE_TOKEN`과 테스트 Plane work item id가 준비됐는지 secret 값 없이 확인한다.
- [x] `./bin/plane-smoke` read-only lookup smoke를 실제 dev Plane에 실행하고 token 없는 stdout/stderr를 기록한다.
- [x] `PLANE_SMOKE_APPLY=1 ./bin/plane-smoke` write smoke를 테스트용 work item에 실행하고 token 없는 stdout/stderr를 기록한다.
- [x] 실제 smoke 성공 결과에 맞춰 `agent-ops/roadmap/milestones/plane-thin-e2e-loop.md`의 실제 smoke 항목만 갱신한다.
- [x] CODE_REVIEW-*-G??.md의 구현 에이전트 소유 섹션을 실제 구현 내용과 검증 출력으로 채운다. 이 항목이 완료되기 전에는 구현이 완료된 것이 아니다.

### [REVIEW_PLANE-1] 실제 Plane smoke evidence 확보

#### 문제

1차 구현은 command, wrapper, README, unit test를 추가했지만 실제 Plane smoke는 실행하지 못했습니다. `code_review_cloud_G07_0.log`에는 `PLANE_TOKEN=not_set`이 기록되어 있고, `plan_cloud_G07_0.log`는 token 또는 test work item이 없으면 task를 완료 처리하지 말라고 명시합니다.

#### 해결 방법

유효한 `PLANE_TOKEN`과 테스트용 work item id가 준비된 환경에서 read-only smoke와 write smoke를 모두 실행합니다.

Before:

```text
PLANE_TOKEN=not_set
실제 Plane lookup/comment/state update 미실행
```

After:

```text
lookup ok: id=<test-work-item-id> name=<work-item-name>
comment ok
state update ok: state_id=<state-id>
```

실행 출력에는 token 값이 없어야 합니다. 실패 출력에 token 값이 섞이면 기록 전에 원인을 수정하고, token 없는 형태로 재검증합니다.

#### 수정 파일 및 체크리스트

- [x] `agent-ops/roadmap/milestones/plane-thin-e2e-loop.md`: 실제 성공한 smoke 항목만 체크한다.
- [x] `services/core/cmd/plane-smoke/main.go`: 실제 smoke 실패가 command 결함을 드러낼 때만 최소 수정한다. (수정 필요 없음)
- [x] `services/core/cmd/plane-smoke/main_test.go`: command 수정이 있으면 관련 unit test를 보강한다. (수정 필요 없음)
- [x] `services/core/internal/adapters/plane/client.go`: 실제 Plane API 계약 mismatch가 확인될 때만 최소 수정한다. (수정 필요 없음)
- [x] `services/core/internal/adapters/plane/client_test.go`: adapter 수정이 있으면 path/header/body/error test를 보강한다. (수정 필요 없음)
- [x] `CODE_REVIEW-cloud-G07.md`: read-only/write smoke의 token 없는 실제 stdout/stderr를 기록한다.

#### 테스트 작성

command 또는 adapter 수정이 없으면 새 unit test는 추가하지 않는다. 실제 smoke 실패로 코드 수정이 필요해지면 해당 behavior를 mock test로 먼저 고정한다.

#### 중간 검증

```bash
cd services/core && go test -count=1 ./cmd/plane-smoke ./internal/adapters/plane
```

예상 결과: smoke command와 Plane adapter package 테스트가 통과한다.

```bash
cd services/core && PLANE_BASE_URL="https://plane.toki-labs.com" PLANE_TOKEN="$PLANE_TOKEN" PLANE_WORKSPACE_SLUG="general" PLANE_PROJECT_ID="a6beb42f-7a8a-410c-b50f-ea3ca94828f3" PLANE_WORK_ITEM_ID="<test-work-item-id>" ./bin/plane-smoke
```

예상 결과: `lookup ok`와 `write smoke skipped`가 출력되고 token은 출력되지 않는다.

```bash
cd services/core && PLANE_BASE_URL="https://plane.toki-labs.com" PLANE_TOKEN="$PLANE_TOKEN" PLANE_WORKSPACE_SLUG="general" PLANE_PROJECT_ID="a6beb42f-7a8a-410c-b50f-ea3ca94828f3" PLANE_WORK_ITEM_ID="<test-work-item-id>" PLANE_SMOKE_COMMENT="NomadCode core Plane smoke" PLANE_SMOKE_STATE_ID="ea2e5b48-8bf1-4723-b749-de7723be41e9" PLANE_SMOKE_APPLY=1 ./bin/plane-smoke
```

예상 결과: `lookup ok`, `comment ok`, `state update ok`가 출력되고 token은 출력되지 않는다.

## 수정 파일 요약

| 파일 | 항목 |
|------|------|
| `agent-ops/roadmap/milestones/plane-thin-e2e-loop.md` | REVIEW_PLANE-1 |
| `services/core/cmd/plane-smoke/main.go` | REVIEW_PLANE-1, 필요 시 |
| `services/core/cmd/plane-smoke/main_test.go` | REVIEW_PLANE-1, 필요 시 |
| `services/core/internal/adapters/plane/client.go` | REVIEW_PLANE-1, 필요 시 |
| `services/core/internal/adapters/plane/client_test.go` | REVIEW_PLANE-1, 필요 시 |

## 최종 검증

```bash
cd services/core && go test -count=1 ./...
```

예상 결과: 모든 core package 테스트가 통과한다. cache output은 허용하지 않는다.

```bash
cd services/core && PLANE_BASE_URL="https://plane.toki-labs.com" PLANE_TOKEN="$PLANE_TOKEN" PLANE_WORKSPACE_SLUG="general" PLANE_PROJECT_ID="a6beb42f-7a8a-410c-b50f-ea3ca94828f3" PLANE_WORK_ITEM_ID="<test-work-item-id>" PLANE_SMOKE_COMMENT="NomadCode core Plane smoke" PLANE_SMOKE_STATE_ID="ea2e5b48-8bf1-4723-b749-de7723be41e9" PLANE_SMOKE_APPLY=1 ./bin/plane-smoke
```

예상 결과: 실제 Plane test work item에 comment 생성과 state update가 성공하고, token은 stdout/stderr에 출력되지 않는다.

모든 코드 변경 완료 후 반드시 `CODE_REVIEW-*-G??.md`의 구현 에이전트 소유 섹션을 채운다. 이 파일 작성이 구현의 마지막 단계다.
