<!-- task=01+02_runtime_context plan=0 tag=REFACTOR -->

# Runtime Context Plan

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

**필수 경고: 구현 마지막 단계에서 `CODE_REVIEW-*-G??.md`의 구현 에이전트 소유 섹션을 모두 채워야 한다. 이 파일이 채워지기 전에는 작업이 완료된 것이 아니다.**
구현 체크리스트를 순서대로 완료하고 실제 검증 출력을 review stub에 기록한다.
review 파일의 아카이브 지시와 `코드리뷰 전용 체크리스트`는 리뷰 에이전트 전용이다.

## 배경

property, commonData, commandStates, dataCommandMap이 `Application.instance` mutable fields로 직접 노출되어 있다.
AI가 변경 범위를 작게 유지하려면 실행 상태를 `ExecutionContext`로 모으고 기존 API는 호환층으로 유지해야 한다.

## 분석 결과

### 읽은 파일

- `agent-ops/skills/common/plan/SKILL.md`
- `agent-ops/rules/project/domain/core/rules.md`
- `agent-ops/rules/project/domain/command/rules.md`
- `agent-ops/rules/project/domain/pipeline/rules.md`
- `lib/oto/application.dart`
- `lib/oto/core/tag_system.dart`
- `lib/oto/commands/command.dart`
- `lib/oto/pipeline/pipeline_exe.dart`
- `lib/oto/pipeline/pipeline_exe_handle.dart`
- `test/test.dart`

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

- `Application.property` 호환 getter/setter가 context를 backing store로 쓰는지 테스트 없음.
- `TagSystem.setPropertyValue()`와 tag read가 context를 경유하는지 테스트 없음.
- pipeline state update가 context commandStates를 갱신하는지 테스트 없음.

### 심볼 참조

- rename/remove 예정 심볼: none.
- 직접 mutable state 접근: `lib/oto/core/tag_system.dart:109`, `137`, `168`; `lib/oto/commands/command.dart:141`, `145`; `lib/oto/pipeline/pipeline_exe.dart:58`, `69`, `92`; `lib/oto/pipeline/pipeline_exe_handle.dart:47`, `75`, `94`.

### 범위 결정 근거

- 이 task는 context 저장소와 호환 API만 도입한다.
- pipeline executor 생성자 주입, command runtime 주입, registry spec은 후속 task에서 처리한다.

### 빌드 등급

- build lane: `cloud-G07` — 전역 상태 접근 경로를 바꾸는 cross-domain 리팩토링이다.
- review lane: `cloud-G07` — 기존 API 호환성과 state isolation을 함께 확인해야 한다.

## 구현 체크리스트

- [ ] [REFACTOR-1] `ExecutionContext`를 추가하고 Application mutable state를 context로 위임한다.
- [ ] 모든 중간 검증과 최종 검증을 실행하고 실제 출력을 `CODE_REVIEW-*-G??.md`에 기록한다.
- [ ] CODE_REVIEW-*-G??.md의 구현 에이전트 소유 섹션을 실제 구현 내용과 검증 출력으로 채운다. 이 항목이 완료되기 전에는 구현이 완료된 것이 아니다.

## 의존 관계 및 구현 순서

- `agent-task/01_test_baseline/complete.log`가 있어야 시작한다.
- `agent-task/01+01_application_result_contract/complete.log`가 있어야 시작한다.
- 이 task 완료 후 command IO와 command catalog task를 시작한다.

### [REFACTOR-1] ExecutionContext 도입

#### 문제

`TagSystem`과 `Command`가 `Application.instance` 상태에 직접 접근한다.

```dart
// lib/oto/core/tag_system.dart:109
Application.instance.property[key] = value;

// lib/oto/commands/command.dart:140
Map<String, dynamic> get property {
  return Application.instance.property;
}
```

#### 해결 방법

`lib/oto/core/execution_context.dart`를 추가한다.
`Application`은 `context`를 소유하고 기존 `property`, `commonData`, `commandStates`, `dataCommandMap` getter/setter를 context 위임으로 유지한다.

```dart
// lib/oto/core/execution_context.dart
class ExecutionContext {
  DataCommon? commonData;
  Map<String, dynamic> property = {};
  Map<String, CommandState> commandStates = {};
  Map<String, DataCommand> dataCommandMap = {};
}
```

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

- [ ] `lib/oto/core/execution_context.dart` 추가
- [ ] `lib/oto/application.dart`에 `context`와 호환 getter/setter 추가
- [ ] `lib/oto/core/tag_system.dart`가 context를 경유하도록 수정
- [ ] `lib/oto/commands/command.dart`가 context를 경유하도록 수정
- [ ] pipeline files의 direct access 제거 여부는 최종 rg로 확인하되, constructor 주입은 하지 않음

#### 테스트 작성

- 작성: `test/oto_context_test.dart`
- 테스트명: `context backs application compatibility accessors`, `tag system reads and writes through execution context`
- 목적: context 도입 후 기존 API와 tag 동작 유지 검증

#### 중간 검증

```bash
dart test test/oto_context_test.dart
```

예상: context 테스트 통과.

## 수정 파일 요약

| 파일 | 항목 |
|------|------|
| `lib/oto/core/execution_context.dart` | REFACTOR-1 |
| `lib/oto/application.dart` | REFACTOR-1 |
| `lib/oto/core/tag_system.dart` | REFACTOR-1 |
| `lib/oto/commands/command.dart` | REFACTOR-1 |
| `test/oto_context_test.dart` | REFACTOR-1 |

## 최종 검증

```bash
dart analyze
```

예상: `No issues found!`

```bash
dart test
```

예상: 모든 테스트 통과.

```bash
rg --sort path -n "Application\\.instance\\.(property|commonData|commandStates|dataCommandMap)" lib/oto/core lib/oto/commands/command.dart
```

예상: 결과 없음.

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