# Phase II — 정류장(야외) shared-model 구도 가이드 설계 초안

> 2026-06-29. 작성=Claude. 상태=**설계 초안 (Codex 의논 전, 미구현)**. 커밋/구현은 사용자 GO 후.
> 절대 제약: 하드코딩/시나리오 의존 0(코드·프롬프트·docstring·갤러리), flag 게이트, 기존 모듈
> 삭제 0(신규 helper/manifest 필드로 확장), 프롬프트 새 버전, Codex=방향/리뷰(main 직접수정 X).

---

## 0. 한 줄 요약

야외 구도 가이드의 **per-shot 독립 스케치가 환경 구조물을 발명**(서양식 셸터 등)해 nb2 still 의
장소 정체성을 덮어쓰는 봉합 결함(§4e-B)을, **하나의 site-layout master(이미 존재)에서 카메라별
가이드를 파생**하는 shared-model 로 구조적으로 제거한다. 핵심 원칙(Codex 합의) = "가이드 부착은
기본값이 아니다 — no-guide 가 부족하거나 per-shot 가이드가 harm 낼 때만, 그리고 그때는 per-shot
독립 발명이 아니라 공유 master 파생으로."

---

## 1. 현 production 코드 (HEAD b389101d, option C, 검증됨)

### 1.1 데이터 흐름 (전부 현존 심볼, codegraph 확인)
1. `outdoor_site_layout_plan.detect_site_seeds` — selected × outdoor(is_indoor=false) ×
   character_angles **2인+** seed, location 별 그룹 (zoom pair/1인 이동 제외).
2. `outdoor_site_layout_provider.emit_site_layout` (LLM1, `build_site_layout_user_prompt`) →
   **site-layout master**: `{landmarks[폴리곤 0-100], cameras[shot별 pos/look_at], figures[shot별 pos/moving_toward]}`.
   ★이것이 PoC 가 쓴 "공유 master" 와 동일 구조.
3. `build_shot_spatial_summary` — master 좌표 → SHOT별 SCENE GEOGRAPHY 텍스트 (순수 좌표산술,
   LLM 0). path 판정 aspect≥3.
4. `composition_guide_shot_keys` (G1 기하: receding mover, NEAREST≠mover) → 후보 샷.
5. `judge_composition_guide_applicable` (G2 의미 judge, gemini-pro, default-deny) → admitted.
6. `composition_continuity_chain(admitted_keys)` — same-scene 그룹, shot_index 정렬,
   **첫=mode 'sketch' / 이후='continuity_anchor'(anchor_source=직전 admitted)**.
7. 첫 샷: `generate_composition_brief`(gemini) → `generate_composition_sketch`(**gpt-image-2 마네킹
   스케치**) → `attach_composition_guide_ref` 가 composition_guide ref 로 nb2 에 부착.
8. 이후 샷: `_attach_continuity_anchor` — anchor_source 의 **현재-run v2 bytes** 를 prev-shot ref
   로 명시 교체 (stale fallback 금지, dep-edge + batch barrier 로 ordering 보장).

### 1.2 구조 결함 (§4e-B, production 에 여전히 존재)
- **R1 (스케치 내용)**: 첫 샷 gpt-image-2 마네킹 스케치가 환경 **건축 구조물을 발명**한다.
  "surface detail 복사금지" 지시로는 구조물 누출을 못 막음. nb2 가 그 발명 셸터를 그려 장소
  정체성(한국식 정류장)을 덮어씀. **무가이드 establishing 샷이 더 정확한 장소를 냈다**(통제비교).
- **R2 (그룹핑)**: G1/G2 게이트(2인+ receding departure)가 진짜 첫 **establishing 샷(흔히 1인)**
  을 그룹에서 배제 → departure 샷이 anchor 가 되고, 그 anchor 가 셸터를 발명. 사용자 §4c 의도는
  "establishing 샷이 anchor, 나머지가 그 v2 참조" 였으나 현 구현은 어긋남.

---

## 2. PoC 검증 레버 (전부 ~/tmp, 미커밋 — [[session-20260627-twod5-bfirst-poc]])

| 레버 | 무엇 | PoC 결과 |
|---|---|---|
| **L-A shared-model** | 한 master(site layout) → 1콜 2패널 카메라뷰 시트 → 패널 crop = 샷별 가이드 | **야외 멀티카메라 강한 PASS**. 양 패널 동일 평지붕 셸터(대조 per-shot=아치/석벽 발명). |
| **L-B 환경-free 스케치(A')** | 스케치=인물+추상 framing/지면만, 건축구조물 0, 환경 정체성=bg ref | Phase2 PASS. 구조물 발명 0, 본문↔스케치 충돌 0. |
| **L-C chaining** | 샷1 anchor 생성 → 후속샷이 [master+샷1] 멀티 edit 으로 디자인 상속 | 작동(평지붕 상속). **단 anchor 품질 게이트 필수**(샷1 틀리면 전파). |
| **L-D no-guide** | nb2 prior + 씬 프롬프트만 | 쉬운 위치는 충분(cross-shot 일관). |

★STEP2 transfer 의 가장 강한 증거: **현 production per-shot 가이드(L-B 대조군)가 오히려 봉합을
유발**(구조 발명 + 마네킹→석상 leakage). shared-model/no-guide 로 교체 시 해소.

---

## 3. Codex 기존 합의 (2026-06-28, [[session-20260628-corpse-outdoor-production-plan]] §4)

- "PoC 두 방식 전면 이식" 아님 → **검증된 실패모드별 좁게 flag-on**.
- **대원칙: 가이드 부착은 기본값이 아니다** — no-guide baseline 부족 or 기존 per-shot guide 가 harm 낼 때만.
- 정책 순서: (1) per-shot 독립 가이드 harm 제거 + no-guide 허용 → (2) guide 필요 판정된 continuity
  group 만 shared-model-derived → (3) 구조 디자인 상속 핵심 case 는 chaining/current-run anchor
  propagation(단 anchor quality gate). 2패널 시트 = guide-internal 검증/동시 카메라 설계용.
- **기존 outdoor_site_layout 확장**(신규 대형 모듈 X → step 안 helper/manifest 필드).
- ★production path 현실안 = "shared model 로 anchor shot guide 생성 → 후속 shot 은 anchor guide
  를 visual continuity source 로 받는 chain".

---

## 4. 제안 설계 — 단계적 (foundation-first)

> 핵심 통찰: **option C 의 chaining(continuity_anchor)은 이미 production 에 있다.** 문제는 (R2)
> 잘못된 샷이 anchor 가 되고 (R1) 그 anchor 가 per-shot 독립 스케치로 구조물을 발명하는 것.
> 따라서 Phase II = "anchor 를 올바른 샷으로 + anchor 가이드를 master 파생/환경-free 로".

### II-1 (foundation) — anchor 가이드 harm 제거: per-shot 독립 스케치 → master 파생
**무엇**: 첫(anchor) 샷의 가이드 생산을 현 `generate_composition_sketch`(gpt-image-2, brief→독립
스케치, 환경 발명) 에서 **site-layout master 파생**으로 교체.
- master = 이미 존재하는 LLM1 layout(`emit_site_layout`)의 좌표.
- 결정론 PIL clean birdseye(색 폴리곤 + 카메라 wedge, 글자 0) → gpt-image-2 **edit**(시각 ref =
  clean birdseye)로 anchor 카메라뷰 1패널 파생 → 그 패널을 composition_guide ref 로 부착.
- 좌표산술 per-camera brief(depth ordering / screen L-C-R / 공유 구조물 invariant / figure 상대
  스케일) = 전부 dot-product, LLM 의미판정 0, 이름 0. (PoC `compute_camera_brief` 검증.)
- **효과**: 구조물이 master(공유)에서 와서 발명 불가 + per-shot 독립 발명 제거 → R1 해소.
- flag: `outdoor_composition_guide_shared_model_enabled` (default OFF). 기존 sketch 경로는 flag
  OFF 시 그대로(byte-identical) — 삭제 0.

### II-2 — multi-camera 그룹: 1콜 2패널 시트 → 패널 crop
**무엇**: 같은 장소에 **카메라가 실제로 다른 샷이 ≥2개**인 continuity group 은 1콜 2패널 시트로
파생(샷마다 별도 콜 대신) → 패널 crop = 각 샷 가이드. cross-camera 일관 by construction.
- 게이트: continuity group 멤버 ≥2 AND 카메라 pos/look_at 가 좌표상 유의미하게 다름(좌표산술).
- 단발/유사카메라 = II-1 단일 파생 or no-guide.

### II-3 — 그룹핑 정렬 (R2): establishing 샷이 anchor
**무엇**: continuity group 의 anchor 를 "G1/G2-admitted 첫 샷" 이 아니라 **같은 장소 group 의
establishing(첫 shot_index, 장소 정의) 샷**으로. departure 게이트(G1/G2)는 이제 "anchor 가
가이드를 받을지" 가 아니라 "어느 샷이 가이드 대상인지" 보조 신호로만.
- ★scope 주의: `detect_site_seeds`(2인+ 게이트)를 건드리면 범위 확대. **대안** = seed 는 그대로
  두되, continuity group 형성 시 같은 location 의 establishing 샷을 anchor 후보로 포함(좌표/
  selected 기반, 글자판정 0). Codex 와 scope 합의 필요.

### II-4 (정책) — no-guide 허용 + acceptance 3단계 게이트
- 항상-부착 폐기. 부착 판정 = (a) no-guide cross-shot drift 위험 or (b) per-shot harm 회피 필요
  일 때만. 그 외 no-guide.
- acceptance: no-guide 실패 → per-shot harm → shared-model 개선 순으로 입증.

---

## 5. ★Codex 의논 포인트 (peer, 결정 필요)

- **Q1 (첫 증분 범위)**: II-1(anchor 가이드 harm 제거 = master 파생, R1) 을 단독 first 증분으로
  하고 II-2/II-3 는 후속? vs II-1+II-3(그룹핑까지) 묶음? — 나는 **II-1 단독 first** 선호(좁고
  안전, R1 이 봉합의 직접 원인). II-3 는 seed 게이트 충돌 risk 라 분리.
- **Q2 (anchor 가이드 생산 메커니즘)**: master 파생(L-A, gpt-image-2 edit) vs 환경-free 스케치
  (L-B, A') — 둘 다 R1 해소. master 파생이 cross-camera 일관까지 주나 PIL birdseye 결정론 코드
  필요. 환경-free 스케치는 기존 brief→sketch 경로 최소수정. **어느 것을 production anchor
  producer 로?** (나는 master 파생 선호 — 사용자가 shared-model 지정 + cross-camera 일관.)
- **Q3 (게이트)**: shared-model 가이드 trigger = 현 G1/G2(departure) 유지? vs same-place
  multi-camera group 으로 일반화? default-deny 유지 전제.
- **Q4 (no-guide 기본화 강도)**: II-4 를 II-1 과 함께 도입(부착 판정 재설계)? vs II-1 은 기존
  게이트 위에 producer 만 교체하고 no-guide 정책은 후속?
- **Q5 (PoC→production 이식 경계)**: PoC 의 PIL birdseye/2패널 edit/좌표산술 brief 코드를
  production helper 로 generic 재작성(시나리오 토큰 0, manifest/diagnostic only). 동의?

---

## 6. 비범위 / 가드
- Phase I(옥탑방 시신) 커밋과 절대 분리 — prompt_service/scene_reference_service 공유 경로 scope guard.
- PoC 자산(~/tmp/geum_panel_sheet/*) 절대 커밋 금지. production 엔 generic helper 만.
- 완성도 = canary + 갤러리 육안(테스트 통과 아님). 단 결정론 게이트/chain/config_hash 는 TDD 유효.

---

## 7. ★확정 v1 = II-1 단독 (Codex APPROVED_WITH_NARROW_SCOPE 반영, 2026-06-29)

Codex peer 리뷰 5문답 합의 → v1 범위를 **II-1 단독**으로 확정. II-2/II-3/II-4 는 후속 wave.

### 7.1 v1 정확한 범위 (II-1 only)
**현 admitted set(G1/G2 그대로) 안에서, 첫(anchor)샷의 가이드 producer 만 교체.**
per-shot 독립 마네킹 스케치(`generate_composition_sketch`, gpt-image-2, 환경 발명) →
**site-layout master 파생 layout-only 카메라뷰 control sketch**.

### 7.2 ★Q2 핵심 제약 — layout/geometry-only (appearance 발명 금지)
master 는 좌표/폴리곤일 뿐 실제 디자인 SOT 아님 → gpt-image-2 가 roof/material/style 발명하면
R1 이 다른 형태로 재발. 따라서:
- producer = "clean birdseye(글자 0, 색 폴리곤+카메라 wedge) + 좌표산술 camera brief →
  gpt-image-2 **edit** → 카메라뷰 control sketch".
- label/prompt 에 명시(generic, 시나리오토큰 0): **"copy spatial layout, depth, figure
  placement, major landmark envelope only; do NOT define material/style/architectural design."**
- 역할 분리: **master guide = anchor 샷의 카메라/깊이/배치 안정화 채널** / 실제 디자인 상속 =
  chaining(continuity_anchor current-run v2) + bg ref 채널. 둘을 섞지 않음.

### 7.3 ★안전가드 (harm 재발 방지, 정책 재설계 아님)
- `shared_model_enabled=True` 경로: **old per-shot `generate_composition_sketch` 호출 금지**.
- shared-model 생성 **실패 시 = no-guide + diagnostic** (old sketch fallback 절대 금지).
- 기존 부착 정책(G1/G2 admitted, continuity_anchor chain, dep edge, current-run v2 bytes)은
  그대로 — II-1 은 "정책 불변, harmful producer 만 제거" 로 측정 가능해야 함.

### 7.4 진단 manifest (II-1 이 "올바른 anchor 샷"까지 해결한다고 주장 X — 정직성 가드)
manifest 에 후속 판단용: `admitted_anchor`, `excluded/possible establishing 후보`,
`no_guide_candidate`, `producer_kind`(shared_model_camera_guide), `guide_generation_status`,
`master_layout_hash`, `camera_brief_hash`, `guide_prompt_hash`. config_hash 에 flag/model/
prompt_version/**helper_version** 접기.

### 7.5 코드 분리 (Codex 권고)
- `outdoor_site_layout_plan.py`: 순수 좌표산술 helper `compute_camera_brief`,
  `build_clean_birdseye_spec` (LLM 0, dot-product, 이름 0).
- `outdoor_site_layout_provider.py`: 이미지 생성 `generate_shared_model_camera_guide`.
- `outdoor_site_layout_step.py`: manifest/cache/diagnostics 배선 + producer 분기(flag).
- 모델 입력 clean birdseye = 글자/라벨 0. 라벨 버전은 review_html/gallery 전용.

### 7.6 결정론 테스트 (TDD 유효)
1. flag OFF → byte-identical/no-op.
2. shared_model ON → old `generate_composition_sketch` 호출 0.
3. shared-model 생성 실패 → composition guide 미부착 + diagnostic, old sketch fallback 0.
4. clean birdseye 모델입력에 text/labels 0.
5. `compute_camera_brief` = 좌표산술 deterministic 계약(좌/우/깊이/relative scale).
6. continuity_anchor 경로 = 기존 current-run v2 bytes 교체 + dep edge 불변.

### 7.7 canary = 기존 station group, 3단 판정 분리
1. **guide 자체**: 구조물 발명 / 텍스트 / leakage 0.
2. **final still**: prompt_used / ref 라벨(layout-only 제약 반영, as-is 0).
3. **final 육안**: no western shelter / stone leakage, place identity 유지, chaining source 정상.
- II-1 단독 PASS 범위 = **"R1 harm 제거"까지만**. establishing anchor(R2)는 II-3 후보로 기록.

### 7.8 후속 wave (v1 비범위, 진단으로 관찰)
- II-2 multi-camera 1콜 2패널 시트(같은 장소 카메라 ≥2 유의미 다름).
- II-3 그룹핑 정렬(establishing anchor) — detect_site_seeds 2인 게이트 충돌 risk, 별도 wave.
- II-4 no-guide 기본화 + 부착 판정 재설계 + same-place multi-camera 승격(3조건 관찰 group 만).

---

## 8. 구현 + canary 결과 (2026-06-29)

### 8.1 구현 (HEAD b389101d 위, flag default OFF, 미커밋)
5 파일 +834/-4: plan.py(compute_camera_brief/build_clean_birdseye_spec/_centroid/_cam_axes/
_project) · provider.py(generate_shared_model_camera_guide/_render_clean_birdseye_png/
SHARED_MODEL_CAMVIEW_SYSTEM/SHARED_MODEL_GUIDE_VERSION) · step.py(sketch 분기 producer 교체
+config_hash+manifest 진단) · config.py(flag) · test +7. 결정론 32(신규7)+소비경로 166 green.

### 8.2 canary tier1 (실 gpt-image-2, osl-l11/shot6, 7bea6537 layout)
production `generate_shared_model_camera_guide` 직접 호출. 갤러리 8899/phase2_canary/results.html.
- **NEW (master 파생, layout-only)** = 평지붕 개방 셸터 **외곽선만**(기둥/벤치 footprint) + 마네킹
  2인(전경 큰 혜수 / 원경 작은 수리영 = depth ordering) + 수평선 LEVEL + 도로 receding. **재질/
  양식/장식/글자 0** = layout-only 제약 준수.
- **OLD (per-shot 독립 스케치, 현 production)** = **아치 유리셸터 + 석벽 + 야자수 + 울창한 수풀/
  펜스/쓰레기통/원경 건물·산 발명**(§4e-B R1 harm 정확 재현).
- birdseye(모델 입력) = 색 폴리곤+카메라 wedge+figure dot, **글자 0**(test+육안 확인).
- 판정(Claude 육안) = **tier1 R1 harm 제거 강한 PASS**(과장 없음). establishing anchor(R2)=II-3.
- tier3(final still 육안)은 PoC([[session-20260627-twod5-bfirst-poc]] STEP2: shared=clean /
  per-shot=아치지붕 발명)에서 이미 검증 — 원하면 production 코드로 재실행 가능(별도).

### 8.3 상태
설계 확정(Codex APPROVED_WITH_NARROW_SCOPE) → 구현 완료 → 결정론 green → canary tier1 육안 PASS →
Codex 코드리뷰 요청 송신(diff 5파일) + 사용자 육안 대기. **커밋은 사용자 GO 후**(scope=Phase II II-1
단독, Phase I/TASK3 와 분리). PoC 자산·canary 드라이버는 커밋 안 함.
