<!-- task=m-workspace-port-env-standardization/03+01,02_remote_smoke_evidence plan=0 tag=TEST -->

# Plan - TEST

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

`CODE_REVIEW-cloud-G07.md`의 구현 에이전트 소유 섹션을 채우기 전까지 구현은 완료가 아니다. 먼저 같은 task group의 `01_compose_env_defaults`와 `02+01_runtime_config_docs`가 PASS되어 `complete.log`를 남겼는지 확인한다. 이 plan은 원격 runner/code-server evidence가 중심이므로 실행 불가 상태를 숨기지 말고 실제 stdout/stderr와 blocker를 review stub에 기록한다.

## 배경

포트 기본값 rollout은 line-level 수정만으로 완료할 수 없다. Docker compose, Control Plane wire, client build/runtime URL, Edge/OpenAI smoke가 새 슬롯에서 같이 동작해야 한다. 이 subtask는 앞선 두 split 작업의 결과를 실제 검증으로 묶고 roadmap task completion evidence를 남긴다.

## 사용자 리뷰 요청 흐름

구현 중 blocker는 active review stub의 `사용자 리뷰 요청` 섹션에 기록한다. 구현 에이전트는 채팅에서 직접 질문하거나 선택지를 제시하지 않으며, code-review가 사용자 리뷰 요청의 정당성을 판단한다.

## Roadmap Targets

- Milestone: `agent-roadmap/phase/automation-runtime-bridge/milestones/workspace-port-env-standardization.md`
- Task ids:
  - `port-default-rollout`: `.env.example`, `docker-compose.yml`, config/default, app README, `agent-test/local`의 포트 기본값과 검증 명령을 표준 후보에 맞춰 정렬한다.
- Completion mode: check-on-pass

## 분석 결과

### 읽은 파일

- `agent-roadmap/current.md`
- `agent-roadmap/phase/automation-runtime-bridge/milestones/workspace-port-env-standardization.md`
- `docker-compose.yml`
- `.env.example`
- `scripts/e2e-control-plane-edge-wire.sh`
- `scripts/e2e-smoke.sh`
- `scripts/e2e-openai-ollama.sh`
- `scripts/dev/web.sh`
- `Makefile`
- `agent-test/local/rules.md`
- `agent-test/local/testing-smoke.md`
- `agent-test/local/platform-common-smoke.md`
- `agent-test/local/client-smoke.md`
- `agent-test/local/control-plane-smoke.md`
- `agent-test/local/edge-smoke.md`
- `agent-test/local/node-smoke.md`

### 테스트 환경 규칙

- 선택 test_env: `local`
- `agent-test/local/rules.md`를 읽었다.
- 적용 profile: `testing-smoke`, `platform-common-smoke`, `client-smoke`, `control-plane-smoke`, `edge-smoke`, `node-smoke`
- Docker compose, Flutter client runtime, field/bootstrap, external runtime evidence는 원격 runner/code-server에서 수행한다.
- local uncommitted 변경이 원격 checkout에 동기화되지 않으면 원격 검증 완료로 보지 않는다.
- token/secret 원문은 tracked 파일과 review output에 기록하지 않는다.

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

- 앞선 split의 unit tests는 default parsing과 일부 client config를 커버하지만 실제 port collision, compose service health, browser-facing URL은 커버하지 않는다.
- `make test-control-plane-edge-wire`는 Control Plane-Edge wire를 커버하지만 compose web service와 DB/cache host publish는 별도 compose evidence가 필요하다.
- OpenAI-compatible field slot `18081`은 provider/runtime 상태에 의존하므로 failure는 환경 blocker와 제품 regression을 구분해 기록해야 한다.

### 심볼 참조

- none

### 분할 판단

- split decision policy를 먼저 평가했다.
- 이 plan은 `03+01,02_remote_smoke_evidence`이므로 predecessors `01`, `02`가 필요하다.
- predecessor `01`: `agent-task/m-workspace-port-env-standardization/01_compose_env_defaults/complete.log` 또는 matching archive `complete.log`가 필요하다. 작성 시점에는 아직 missing이다.
- predecessor `02`: `agent-task/m-workspace-port-env-standardization/02+01_runtime_config_docs/complete.log` 또는 matching archive `complete.log`가 필요하다. 작성 시점에는 아직 missing이다.
- 이 final validation split만 `Roadmap Targets`를 포함해 `port-default-rollout`을 check-on-pass 대상으로 둔다.

## 의존 관계 및 구현 순서

- `01_compose_env_defaults`와 `02+01_runtime_config_docs`의 `complete.log`가 모두 없으면 구현을 시작하지 않는다.
- predecessor 완료 후 local checkout과 원격 runner checkout이 같은 commit 또는 같은 patch 상태인지 확인한다.
- 원격 runner에서 Docker compose와 Flutter/client runtime evidence를 수집한다.

### 범위 결정 근거

- 이 subtask는 검증/evidence와 필요한 test-rule 문구 보정만 수행한다.
- port default 코드와 compose/env 변경은 predecessors 소유다.
- provider 계정, token, private endpoint를 tracked 파일에 기록하지 않는다.
- code-server 컨테이너 재시작은 사용자가 명시하지 않으면 수행하지 않는다.

### 빌드 등급

- `cloud-G07`: 원격 runner, Docker compose, client runtime, e2e smoke, external runtime blocker 판정이 중심이라 local-only agent가 증거를 안전하게 완결하기 어렵다.

## 구현 체크리스트

- [ ] predecessor `01_compose_env_defaults`와 `02+01_runtime_config_docs`의 `complete.log`를 확인한다.
- [ ] local quick regression을 실행하고 결과를 기록한다.
- [ ] 원격 runner/code-server에서 compose render와 compose service health를 새 host slot으로 확인한다.
- [ ] Control Plane-Edge wire, edge-node smoke, OpenAI-compatible smoke 중 변경 범위에 맞는 smoke를 실행하고 pass/blocker를 분리해 기록한다.
- [ ] 검증 결과에 host/token/credential 원문이 남지 않도록 출력 sanitization 여부를 확인한다.
- [ ] CODE_REVIEW-*-G??.md의 구현 에이전트 소유 섹션을 실제 구현 내용과 검증 출력으로 채운다. 이 항목이 완료되기 전에는 구현이 완료된 것이 아니다.

### [TEST-1] Confirm predecessor completion and local regression

문제: `port-default-rollout`은 compose/env와 runtime/config/docs split이 모두 완료된 뒤에만 완료 evidence를 낼 수 있다. predecessor 완료 없이 smoke만 실행하면 어떤 default가 검증된 것인지 불명확하다.

해결 방법:

- active 또는 archived `complete.log`로 `01`, `02` 완료를 확인한다.
- local Go regression을 먼저 실행해 원격 runner 비용 전에 compile/test regression을 줄인다.

수정 파일 및 체크리스트:

- [ ] source 수정 없음
- [ ] `CODE_REVIEW-cloud-G07.md`: predecessor complete.log path 기록

테스트 작성: 검증-only task이므로 새 테스트 파일은 작성하지 않는다.

중간 검증:

```bash
test -f agent-task/m-workspace-port-env-standardization/01_compose_env_defaults/complete.log || find agent-task/archive -path '*/m-workspace-port-env-standardization/01_compose_env_defaults/complete.log' -print -quit
test -f agent-task/m-workspace-port-env-standardization/02+01_runtime_config_docs/complete.log || find agent-task/archive -path '*/m-workspace-port-env-standardization/02+01_runtime_config_docs/complete.log' -print -quit
go test ./...
```

기대 결과: 두 predecessor complete log가 확인되고 `go test ./...`가 통과한다.

### [TEST-2] Verify remote compose slots

문제: `docker-compose.yml` 변경은 현재 컨테이너에서 Docker-in-Docker로 검증하지 않는다. 원격 runner/code-server에서 새 host publish slot이 충돌 없이 render/health를 통과해야 한다.

해결 방법:

- 변경분을 원격 runner checkout에 동기화한다.
- 원격 runner에서 `.env.example` 기준 compose config와 service health를 확인한다.
- `IOP_EDGE_NODE_TOKEN`은 원격 shell 환경에만 둔다.

수정 파일 및 체크리스트:

- [ ] source 수정 없음
- [ ] `CODE_REVIEW-cloud-G07.md`: 원격 runner path, sync 상태, compose command output 기록

테스트 작성: 새 테스트 파일은 작성하지 않는다.

중간 검증:

```bash
test -n "${IOP_EDGE_NODE_TOKEN:?set IOP_EDGE_NODE_TOKEN in the remote shell}"
docker compose --env-file .env.example config >/tmp/iop-compose-config.out
rg --sort path '18000|13000|15400|16300|19080|19081|19090' /tmp/iop-compose-config.out
docker compose --env-file .env.example up --build -d postgres redis control-plane edge web
curl -fsS http://127.0.0.1:18000/healthz
curl -fsS http://127.0.0.1:18000/readyz
docker compose ps
docker compose down
```

기대 결과: compose render, service startup, health/readiness가 성공한다. 실패 시 port collision, token missing, Docker unavailable, service regression을 구분해 기록한다.

### [TEST-3] Verify wire, client, and Edge input smoke

문제: CP HTTP, wire, web, OpenAI-compatible slots는 별도 entrypoint에서 사용된다. compose health만으로 client config나 Edge input smoke가 새 기준을 따른다고 볼 수 없다.

해결 방법:

- Control Plane-Edge wire smoke를 실행한다.
- client build 또는 Flutter test를 원격 runner에서 실행한다.
- Edge/OpenAI smoke는 provider/runtime 접근 가능 여부를 먼저 기록하고 가능한 경우 실행한다.

수정 파일 및 체크리스트:

- [ ] source 수정 없음
- [ ] `CODE_REVIEW-cloud-G07.md`: smoke command output 기록

테스트 작성: 새 테스트 파일은 작성하지 않는다.

중간 검증:

```bash
make test-control-plane-edge-wire
cd apps/client && flutter test
make client-build-web
./scripts/e2e-smoke.sh
./scripts/e2e-openai-ollama.sh
```

기대 결과: wire/client/e2e smoke가 통과한다. 외부 model/provider 상태 때문에 OpenAI smoke가 불가능하면 실행 전 확인 command와 blocker를 기록하고, 실패가 port regression인지 환경 문제인지 분리한다.

## 수정 파일 요약

| 파일 | 항목 |
|------|------|
| `CODE_REVIEW-cloud-G07.md` | TEST-1, TEST-2, TEST-3 |

## 최종 검증

```bash
test -f agent-task/m-workspace-port-env-standardization/01_compose_env_defaults/complete.log || find agent-task/archive -path '*/m-workspace-port-env-standardization/01_compose_env_defaults/complete.log' -print -quit
test -f agent-task/m-workspace-port-env-standardization/02+01_runtime_config_docs/complete.log || find agent-task/archive -path '*/m-workspace-port-env-standardization/02+01_runtime_config_docs/complete.log' -print -quit
go test ./...
test -n "${IOP_EDGE_NODE_TOKEN:?set IOP_EDGE_NODE_TOKEN in the remote shell}"
docker compose --env-file .env.example config >/tmp/iop-compose-config.out
rg --sort path '18000|13000|15400|16300|19080|19081|19090' /tmp/iop-compose-config.out
docker compose --env-file .env.example up --build -d postgres redis control-plane edge web
curl -fsS http://127.0.0.1:18000/healthz
curl -fsS http://127.0.0.1:18000/readyz
docker compose down
make test-control-plane-edge-wire
cd apps/client && flutter test
make client-build-web
./scripts/e2e-smoke.sh
./scripts/e2e-openai-ollama.sh
```

기대 결과: predecessor completion, local regression, remote compose, wire/client/edge smoke가 통과한다. 불가능한 외부 runtime 검증은 `사용자 리뷰 요청`이 아니라 blocker evidence로 기록하되, port regression과 환경 문제를 구분한다.

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