<!-- task=m-mattermost-nexo-messaging-alignment/01_runner_preflight plan=0 tag=TEST -->

# Plan - TEST Runner Preflight

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

`CODE_REVIEW-cloud-G07.md`의 구현 에이전트 소유 섹션을 실제 구현 내용과 검증 출력으로 반드시 채운다. 검증을 실행하고 실제 stdout/stderr를 붙이며, active 파일은 그대로 둔 채 리뷰 준비를 보고한다. 최종 판정, log rename, `complete.log`, archive 이동은 code-review-skill 전용이다. 사용자 결정, 외부 환경 준비, 범위 충돌 없이는 진행할 수 없으면 review stub의 `사용자 리뷰 요청` 섹션에 정확한 증거를 채우고 멈춘다.

## 배경

현재 마일스톤의 유일한 남은 Task는 실제 Android runner에서 Mattermost server-generated signed push smoke를 재실행하는 일이다. 이 smoke는 local secret, remote Android runner, sibling workspace, Android device/emulator가 모두 준비되어야 의미가 있다. 먼저 preflight를 독립적으로 닫아야 다음 smoke가 환경 문제와 기능 문제를 섞지 않는다.

## 사용자 리뷰 요청 흐름

구현 중 blocker는 active `CODE_REVIEW-cloud-G07.md`의 `사용자 리뷰 요청` 섹션에 기록한다. 형식은 `agent-ops/skills/common/_templates/implementation-user-review-request-section.md`와 같으며, code-review가 검증 후 실제 `USER_REVIEW.md` 작성 여부를 결정한다.

## 분석 결과

### 읽은 파일

- `agent-roadmap/current.md`
- `agent-roadmap/phase/external-integration/PHASE.md`
- `agent-roadmap/phase/external-integration/milestones/mattermost-nexo-messaging-alignment.md`
- `agent-test/local/rules.md`
- `agent-test/local/mobile-smoke.md`
- `agent-test/local/mobile-android-sdk-smoke.md`
- `agent-test/local/mattermost-server-generated-push-smoke.md`
- `agent-ops/rules/project/domain/mobile/rules.md`
- `agent-ops/rules/project/domain/workspace-ops/rules.md`

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

- Remote runner 접근, sibling checkout, Android SDK/device 준비 상태는 automated unit test로 커버되지 않는다. 이 plan은 shell preflight 출력으로만 검증한다.
- Secret 값 자체는 읽거나 기록하지 않는다. `agent-test/local/testing-secrets.md`와 ignored credential asset의 존재만 확인하고, 필요한 값의 원문 확인은 smoke 구현 단계에서 redaction 규칙을 지켜 수행한다.

### 심볼 참조

- none. 이 plan은 symbol rename/remove를 하지 않는다.

### 분할 판단

- split decision policy를 파일 선택 전에 평가했다.
- shared task group: `m-mattermost-nexo-messaging-alignment`
- `01_runner_preflight`: local/remote 환경과 runner 준비 상태를 확인한다.
- `02+01_signed_smoke`: `01_runner_preflight`의 `complete.log` 이후 실제 push smoke와 evidence 기록을 수행한다.
- 자연 의존성이 있다. remote checkout/device가 준비되지 않으면 smoke 결과가 기능 검증이 아니라 환경 blocker가 되므로 split이 안전하다.

### 범위 결정 근거

- 이 plan은 source code, Android native code, `../nexo/packages/messaging_flutter` 구현을 수정하지 않는다.
- Plane/Jira adapter, core Mattermost REST adapter 전체 구현, iOS/macOS native push runtime, Mattermost 제품 UX는 마일스톤 범위 제외다.
- `agent-test/local/testing-secrets.md`와 credential 원문은 읽더라도 review/plan/final output에 기록하지 않는다.

### 빌드 등급

- build lane: `cloud-G07`, review lane: `cloud-G07`.
- 이유: remote shell, Android SDK/device, long-running smoke 전 prerequisite를 판정하는 terminal-agent 작업이다.

## 구현 체크리스트

- [ ] [TEST-1] Local secret/asset/sibling workspace 존재와 remote Android runner checkout/toolchain/device preflight를 실행한다.
- [ ] CODE_REVIEW-*-G??.md의 구현 에이전트 소유 섹션을 실제 구현 내용과 검증 출력으로 채운다. 이 항목이 완료되기 전에는 구현이 완료된 것이 아니다.

### [TEST-1] Runner Preflight

#### 문제

`agent-roadmap/phase/external-integration/milestones/mattermost-nexo-messaging-alignment.md:36`의 남은 Task는 실제 Android runner evidence를 요구한다. `agent-test/local/mattermost-server-generated-push-smoke.md:106`-`113`은 secret, remote sibling workspace, Android device/emulator, redaction 실패를 차단 기준으로 둔다.

#### 해결 방법

Local prerequisite와 remote runner 상태를 먼저 확인한다. Secret 원문은 출력하지 않는다.

Before (`agent-test/local/mattermost-server-generated-push-smoke.md:41`-`47`):

```markdown
- setup:
  - `ssh toki@toki-labs.com`
  - `cd /config/workspace/nomadcode` if that checkout exists; otherwise use the active NomadCode checkout on the host.
  - Remote Android note checked on 2026-05-29: the standard host was reachable, but no `~/works/nomadcode` or `/config/workspace/nomadcode` checkout was found.
  - Android runtime smoke 전에 remote host에 `nomadcode`, `nexo`, `proto-socket` sibling workspace를 준비하거나 동기화한다.
  - `apps/client/assets/mattermost_credentials.json` ignored credential asset을 private input으로 생성한다.
  - If the private environment provides a Mattermost server identifier that appears in FCM payloads as `server_id`, add it as `serverId` or `serverIdentifier` in the ignored credential asset.
```

After: no source/doc change in this preflight task. Record the actual local and remote preflight output in `CODE_REVIEW-cloud-G07.md`.

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

- [ ] `CODE_REVIEW-cloud-G07.md`: local preflight stdout/stderr 기록
- [ ] `CODE_REVIEW-cloud-G07.md`: remote checkout path, branch, commit, Android toolchain/device 출력 기록
- [ ] `CODE_REVIEW-cloud-G07.md`: blocker가 있으면 `사용자 리뷰 요청`에 재개 조건 기록

#### 테스트 작성

- Skip. 이 task는 code behavior를 바꾸지 않고 environment preflight만 수행한다.

#### 중간 검증

```bash
printf 'testing-secrets: '; test -f agent-test/local/testing-secrets.md && echo present || { echo missing; exit 1; }
printf 'credential asset: '; test -f apps/client/assets/mattermost_credentials.json && echo present || { echo missing; exit 1; }
printf 'nexo messaging: '; test -d ../nexo/packages/messaging_flutter && echo present || { echo missing; exit 1; }
printf 'proto-socket dart: '; test -d ../proto-socket/dart && echo present || { echo missing; exit 1; }
printf 'ssh: '; command -v ssh
printf 'flutter: '; flutter --version | head -n 1
git rev-parse --abbrev-ref HEAD
git rev-parse HEAD
```

Expected: every local prerequisite prints `present`; `ssh`, `flutter`, branch, and commit print without exposing secrets.

```bash
ssh toki@toki-labs.com 'set -eu
if [ -d /config/workspace/nomadcode/.git ]; then
  cd /config/workspace/nomadcode
elif [ -d "$HOME/works/nomadcode/.git" ]; then
  cd "$HOME/works/nomadcode"
else
  echo "nomadcode checkout missing"
  exit 2
fi
printf "checkout=%s\n" "$PWD"
git rev-parse --abbrev-ref HEAD
git rev-parse HEAD
test -d ../nexo/packages/messaging_flutter
test -d ../proto-socket/dart
flutter doctor -v
printf "ANDROID_HOME=%s\n" "${ANDROID_HOME:-}"
printf "ANDROID_SDK_ROOT=%s\n" "${ANDROID_SDK_ROOT:-}"
flutter devices
'
```

Expected: remote checkout exists, sibling paths exist, Flutter/Android SDK information is printed, and at least one Android device/emulator is available. If checkout or device is missing and cannot be prepared non-destructively, fill `사용자 리뷰 요청`.

## 수정 파일 요약

| 파일 | 항목 |
|------|------|
| `agent-task/m-mattermost-nexo-messaging-alignment/01_runner_preflight/CODE_REVIEW-cloud-G07.md` | TEST-1 |

## 최종 검증

```bash
test -f agent-task/m-mattermost-nexo-messaging-alignment/01_runner_preflight/CODE_REVIEW-cloud-G07.md
```

Expected: file exists and contains actual preflight output, or a filled `사용자 리뷰 요청` with blocker evidence.

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