<!-- task=m-control-plane-api-data-binding/02+01_execution_surface plan=1 tag=REVIEW_API -->

# Plan - REVIEW_API Client Wiring Test Coverage

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

구현 완료의 마지막 단계는 active `CODE_REVIEW-*-G??.md`의 구현 에이전트 소유 섹션을 실제 구현 내용과 검증 출력으로 채우는 것이다. 검증을 실행하고, 실제 출력과 설계 결정을 기록한 뒤 active 파일을 그대로 둔 채 리뷰 준비를 보고한다. 종결 처리, log rename, `complete.log` 작성, archive 이동은 code-review 스킬 전용이다. 구현 중 사용자만 결정할 항목, 사용자 소유 외부 환경, 범위 충돌이 발견되면 review stub의 `사용자 리뷰 요청` 섹션에 정확한 근거를 남기고 멈춘다. 구현 중 채팅으로 직접 질문하거나 `request_user_input`을 호출하지 않는다.

## 배경

이 후속 루프는 `code_review_local_G06_0.log`의 Required 이슈만 다룬다. 제품 코드의 기본 jobs/executions/artifacts wiring과 console surface tests는 통과했지만, 원 계획의 API-2는 fake read client 기반으로 job/execution/log/artifact data와 empty/error 상태 표시를 모두 검증하라고 요구했다. 현재 `apps/client/test/widget_test.dart`는 새 client wiring의 data path만 검증하므로 empty/error 화면 검증을 보강해야 한다.

## 사용자 리뷰 요청 흐름

구현 중 차단 사항은 active review stub의 `사용자 리뷰 요청` 섹션에 기록한다. 해당 섹션은 `agent-ops/skills/common/_templates/implementation-user-review-request-section.md` 형식을 따른다. 직접 사용자 프롬프트는 금지되며, code-review가 요청 타당성을 검토하고 실제 `USER_REVIEW.md` 작성 여부를 결정한다.

## Roadmap Targets

- Milestone: `agent-roadmap/phase/control-plane-product-surface/milestones/control-plane-api-data-binding.md`
- Task ids:
  - `execution-surface`: Pipelines/Jobs와 Executions 화면이 job/execution read model을 표시하고 로그/아티팩트 진입 위치를 제공한다.
- Completion mode: check-on-pass

## Archive Evidence Snapshot

- Archived plan: `agent-task/m-control-plane-api-data-binding/02+01_execution_surface/plan_local_G06_0.log`
- Archived review: `agent-task/m-control-plane-api-data-binding/02+01_execution_surface/code_review_local_G06_0.log`
- Verdict: FAIL
- Required summary:
  - `apps/client/test/widget_test.dart:381`의 client wiring 테스트가 jobs/executions/artifacts data path만 검증한다. API-2 계획은 fake read client로 job/execution/log/artifact data와 empty/error 상태 표시를 모두 검증하라고 요구했다.
- Affected files:
  - `apps/client/test/widget_test.dart`
  - 필요 시 `apps/client/lib/src/app/oto_client_app.dart`
- Verification evidence from archived loop:
  - `cd packages/flutter/oto_console && flutter test`: 통과
  - `cd apps/client && flutter test`: 통과
  - `git diff --check`: EOF 공백 수정 후 통과
- Allowed archive reread:
  - 위 archived plan/review log 두 파일만 좁게 읽는다.

## 범위 결정 근거

- 이번 후속은 missing test coverage 보강이다. 제품 코드는 테스트가 실제 결함을 드러낼 때만 최소 수정한다.
- Core route/schema, roadmap 문서, 다른 split task(`03+01,02_preview_smoke`)는 수정하지 않는다.
- follow-up route는 `local-G07`이다. 이슈가 명시적이고 deterministic widget tests로 검증 가능하므로 cloud escalation은 필요하지 않다.

## 구현 체크리스트

- [ ] `apps/client/test/widget_test.dart`에 `OtoClientApp` fake read client 기반 jobs/executions/artifacts empty/error wiring tests를 추가한다. 검증: `cd apps/client && flutter test`에서 새 empty/error tests가 함께 통과한다.
- [ ] `git diff --check`를 실행해 task artifact와 Dart test 변경에 whitespace error가 없는지 확인한다.
- [ ] CODE_REVIEW-*-G??.md의 구현 에이전트 소유 섹션을 실제 구현 내용과 검증 출력으로 채운다. 이 항목이 완료되기 전에는 구현이 완료된 것이 아니다.

### [REVIEW_API-1] Client empty/error wiring tests

문제: `apps/client/test/widget_test.dart`의 `OtoClientApp wires jobs, executions and artifacts data state on API success`는 data path만 검증한다. 원 계획은 fake read client로 job/execution/log/artifact data와 empty/error 상태 표시를 모두 확인하라고 요구했으므로, 현재 테스트는 plan completion evidence로 부족하다.

해결 방법: `_registerJobsExecutionsTests()`에 아래 상태를 실제 `OtoClientApp` widget으로 검증하는 테스트를 추가한다.

- no `jobIDs`/`executionIDs`일 때 Pipelines, Executions, Artifacts tab의 empty 문구가 표시된다.
- `fetchJob` error가 Pipelines tab의 `Error loading jobs`와 error message로 표시된다.
- `fetchExecution` error가 Executions tab의 `Error loading executions`와 error message로 표시된다.
- `fetchArtifacts` error가 Artifacts tab의 `Error loading artifacts`와 error message로 표시된다.
- expanded execution detail에서 `fetchLogs` empty/error와 `fetchArtifacts` empty/error가 각각 `Log is empty.`, `Error loading logs: ...`, `No artifacts produced.`, `Error loading artifacts: ...`로 표시된다.

수정 파일 및 체크리스트:

- [ ] `apps/client/test/widget_test.dart`에 중복을 줄이는 test helper를 추가하거나 기존 `_FakeCoreReadClient`를 재사용한다.
- [ ] 새 tests가 `OtoConsoleConfig.serverHttpUrl` 기반 fake client 호출을 유지하는지 확인한다.
- [ ] 테스트가 product behavior gap을 드러내면 `apps/client/lib/src/app/oto_client_app.dart`만 최소 수정하고, 수정 사유를 review stub에 기록한다.

테스트 작성: 작성. 각 상태별로 화면 문구를 assert한다.

중간 검증:

```bash
cd apps/client && flutter test
```

기대 결과: 새 empty/error wiring tests 포함 전체 통과.

## 수정 파일 요약

| 파일 | 항목 |
|------|------|
| `apps/client/test/widget_test.dart` | REVIEW_API-1 |
| `apps/client/lib/src/app/oto_client_app.dart` | REVIEW_API-1, 테스트가 실제 product gap을 드러낼 때만 |

## 최종 검증

```bash
cd apps/client && flutter test
git diff --check
```

기대 결과: 두 명령 모두 통과한다.

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