중복 문서를 통합하고 완료된 구현 계획을 정리한다

This commit is contained in:
2026-09-29 09:08:28 +00:00
parent 08c3d0e936
commit cd6ded4970
9 changed files with 285 additions and 1295 deletions
@@ -1,183 +0,0 @@
# Game clock reconciliation implementation plan
Baseline: `main@b91dcbcaaac5acd4c7349cd3ed0996c547f58756`
Branch: `test/game-clock-reconciliation-20260903`
이 문서는 위 기준선·branch에서 진행한 구현 계획의 기록입니다. 체크 표시는 당시
코드와 집중 검증이 있었다는 뜻이며, 현재 main·배포·운영 검증 상태를 나타내지 않습니다.
현재 동작은 [게임 시계](../architecture/game-clock.md)와
[재정렬 계약](../architecture/game-clock-reconciliation.md), 장애 처리는
[복구 안내](./game-clock-recovery.md)를 읽으세요.
## Milestone 1 - authority and inventory
- [x] Branded `GameTick`, `ObservedGameInstant`, `ScheduleInstant`,
`WallInstant`, and `ClockRevision` boundaries.
- [x] Explicit clock phase and monotonic RUNNING projection.
- [x] Exact alignment arithmetic preserving millisecond/sub-turn remainder.
- [x] Opening tick zero and PREOPEN executable floor in the shared seeder.
- [x] Schema columns for phase, revision, and deadline generation.
- [x] Suspension, participant-checksum, and Redis projection outbox tables.
- [x] Machine-readable DB/Redis/JSON participant inventory and architecture gate.
- [x] Turn flush lock prefix and phase/revision/generation fence.
- [x] Empty and upgraded database migration execution evidence.
## Milestone 2 - exact DB reconciliation
- [x] Suspension start command with DB wall time and idempotent source revision.
- [x] Exact resume plan transaction with deterministic participant lock order.
- [x] SHIFT adapters for cursor, generals, active auctions, message expiry, vote
end, select pool, and NPC selection windows.
- [x] KEEP checksum adapters for occurrences and accepted command coordinates.
- [x] Explicit `LEGACY_COMPLETE_TURNS` and bounded `CATCH_UP` policies.
- [x] Property tests for remaining distance, ordering, and history invariants.
- [x] 24-hour and 65m17.250s PostgreSQL integration evidence.
## Milestone 3 - revisioned Redis and workers
- [x] Projection outbox claimer/retry/recovery state machine.
- [x] Redis active revision and atomic due-pop script.
- [x] Auction OPEN/FINALIZING revision and generation fence.
- [x] Tournament durable tick dual-write and projection rebuild.
- [x] DB-commit/Redis-failure crash-restart test.
- [x] Readiness integration in Gateway/API process health.
## Milestone 4 - command and lifecycle workflows
- [x] All durable input events record accepted tick and accepted revision.
- [x] Processing converts accepted coordinates across revisions or fails closed.
- [x] Gateway pause/resume/open orchestration writes the DB clock phase.
- [x] Unification wait becomes a durable `UNIFICATION_WAIT` suspension.
- [x] Alignment, optional rate change, invader IDs/RNG, creation, first schedule,
outbox, verification, and RUNNING transition form one retry-safe workflow.
- [x] Multi-host drift and general-access/clock-operation deadlock tests.
## Milestone 5 - test-branch release gate
- [x] Full typecheck, architecture, lint, unit, build, and non-conditional
integration suites.
- [x] Dedicated PostgreSQL/Redis conditional integration suite with skip count
recorded.
- [x] Recovery runbook exercised from each incomplete status.
- [x] Admin status/readiness exposes revision, phase, participant checksums, and
incomplete outbox state.
- [ ] User-test deployment evidence is recorded separately from Git push.
- [x] All `FORBID` inventory entries are removed by typed migrations or proven
inactive preconditions.
## Evidence log
### 2026-09-03 - authority foundation
- `pnpm test:bootstrap`: dependency installation, Prisma generation, and package
preparation passed in the dedicated worktree.
- `CI=1 TURBO_CONCURRENCY=1 pnpm typecheck`: 21/21 tasks passed.
- `CI=1 TURBO_CONCURRENCY=1 pnpm test`: 12/12 package tasks passed. Conditional
suites remain classified separately and are not integration evidence.
- `CI=1 TURBO_CONCURRENCY=1 pnpm build`: 26/26 tasks passed.
- `TURBO_CONCURRENCY=1 pnpm lint`: passed with 36 pre-existing frontend
warnings and no errors.
- `pnpm check:architecture`: package boundaries passed; 21 authoritative clock
fields and 18 participants were registered.
- Migration SQL was generated, formatted, validated, and registered as the
release manifest head. All 43 migrations applied to the empty dedicated
PostgreSQL instance. A second schema upgraded from the previous head with an
existing manual `world_state` row and verified `MANUAL:1:1` plus all three
reconciliation tables.
- Dedicated PostgreSQL/Redis fixtures proved exact 24-hour and 65m17.250s gaps,
schedule distance/order preservation, occurrence checksums, live-lease
fencing, a single durable outbox, Redis target revision, and recovery after a
crash between Redis commit and DB finalization.
### 2026-09-03 - revisioned workers and input coordinates
- `CI=1 TURBO_CONCURRENCY=1 pnpm typecheck`: 21/21 tasks passed after the
worker/input contract changes.
- `CI=1 TURBO_CONCURRENCY=1 pnpm test`: 12/12 package tasks passed.
- Dedicated PostgreSQL runs passed `databaseCommandQueue.integration.test.ts`
6/6 and `runtimeClockShiftPersistence.integration.test.ts` 3/3 when executed
sequentially; the latter now clears each single-world fixture before the next
case. Dedicated Redis passed tournament source revision 4/4, including an
atomic stale-clock rejection. API input-event integration passed 13/13.
- The 24-hour/65m17.250s reconciliation suite passed 2/2 after the other DB
suites. Conditional files share a deliberately dedicated schema and are run
sequentially to prevent their fixture cleanup from racing another file.
### 2026-09-03 - Gateway lifecycle authority
- Runtime `PAUSE`/`STOP` starts a durable maintenance suspension before the
Gateway status and process reconciliation change. `RESUME` completes the DB
reconciliation and Redis outbox before the profile becomes `RUNNING`.
- Both an already-built overdue `RESERVED` profile and an overdue `PREOPEN`
profile promote the game DB from `PREOPEN@0` before the Gateway status changes
to `RUNNING`; the Redis clock phase is revision/generation fenced.
- `pnpm --filter @sammo-ts/gateway-api test` passed 313 tests with 35
environment-conditional skips. Gateway typecheck and target lint passed.
### 2026-09-03 - atomic unification wait
- A unification flush now commits the finalization, actionable prompts, and one
deterministic `UNIFICATION_WAIT` suspension together. A late archive failure
rolls the whole boundary back; retry creates one ledger.
- The suspended command queue admits only an invader decision tied to the
active ledger. The daemon-authorized command transaction applies a 36-hour
exact gap, preserves participant positions, changes the fixture rate from 10
to 20 minutes, creates one invader nation and ten deterministic generals with
future first turns, and writes one final-rate projection outbox.
- The dedicated PostgreSQL/Redis fixture reached `RUNNING@2/2` only after the
Redis projection. DB-wall versus a mocked 12-hour host drift and concurrent
general-access lock acquisition completed without drift or deadlock.
- `CI=1 TURBO_CONCURRENCY=1 pnpm typecheck` passed 21/21 tasks,
`CI=1 TURBO_CONCURRENCY=1 pnpm test` passed 12/12 package tasks,
`CI=1 TURBO_CONCURRENCY=1 pnpm build` passed 26/26 tasks, and workspace lint
passed. `pnpm check:architecture` registered 22 authoritative clock fields
and 18 participants.
- Dedicated sequential PostgreSQL/Redis runs passed clock reconciliation 3/3,
atomic unification 1/1, command queue 7/7, runtime clock persistence 3/3,
API input-event boundary 13/13, and tournament revision 4/4: 31/31 enabled
tests with zero skips. The queue and API suites now create and remove their
own clock fixtures so a completed file cannot leak phase or initialization
state into the next file.
- User-test deployment and public runtime evidence remain deliberately open:
Git push is not deployment, and no deployment was authorized in this work.
### 2026-09-03 - completion audit
- The invader response now reads the exact post-alignment world snapshot even
when the turn rate is unchanged. The HWE-shaped regression asserts all ten
first turns are in the aligned next-month window rather than already due.
- The ordinary flush fence now uses the same incomplete-row dual-read rule as
`worldLoader`: a legacy row is `MANUAL` until all four clock snapshot fields
exist. Input-event acceptance remains fail-closed until initialization.
- Auction OPEN/FINALIZING recovery fixtures and direct PROCESSING input-event
fixtures now carry explicit phase/revision/generation coordinates. The
optional Ref-only troop parity suite is registered only in Ref mode, so the
Core conditional gate reports only tests it actually ran.
- `pnpm check:architecture` passed with 22 authoritative fields and all 18
required DB/JSON participants. The gate now rejects duplicate or `FORBID`
participants, missing required participants, and unimplemented/duplicate
Redis participants.
- `CI=1 TURBO_CONCURRENCY=1 pnpm test:integration:conditional` passed 79 files
and 234 tests against isolated PostgreSQL/Redis schemas with zero skipped and
zero failed files.
- On the audited diff, `pnpm check:architecture` passed, full typecheck passed
21/21 tasks, workspace test passed 12/12 tasks, build passed 26/26 tasks, and
workspace lint completed without errors.
The required acceptance cases map to automated evidence as follows:
| Contract | Automated evidence |
| ------------------------------------------------------------------------------------- | ---------------------------------------------------------------------------------------------------------------------------------------------- |
| PREOPEN signed tick, tick-zero opening, executable floor; RUNNING rewind monotonicity | `packages/common/test/gameClock.test.ts`, `app/game-engine/test/scenarioSeeder.test.ts`, `app/gateway-api/test/orchestratorOperations.test.ts` |
| Exact 24-hour and 65m17.250s gaps; ordering, remaining distance, occurrence history | `app/game-engine/test/clockReconciliation.integration.test.ts`, `packages/common/test/gameClock.test.ts` |
| DB commit/Redis failure and incomplete-status recovery | `app/game-engine/test/clockReconciliation.integration.test.ts`, `app/game-engine/test/unificationFinalization.integration.test.ts` |
| Auction OPEN/FINALIZING and tournament revision races | `app/game-api/test/auctionWorker.integration.test.ts`, `app/game-api/test/tournamentStoreRevision.integration.test.ts` |
| Pending commands crossing a clock revision | `app/game-engine/test/databaseCommandQueue.integration.test.ts`, `app/game-api/test/inputEventBoundary.integration.test.ts` |
| Delayed opening | `app/gateway-api/test/orchestratorOperations.test.ts`, `app/game-engine/test/scenarioSeeder.test.ts` |
| 36-hour unification wait, rate change, deterministic retry, future invader turns | `app/game-engine/test/unificationFinalization.integration.test.ts`, `app/game-engine/test/unificationInvaderResume.test.ts` |
| DB wall despite host drift; general-access lock ordering | `app/game-engine/test/clockReconciliation.integration.test.ts`, `app/game-engine/test/profileSchemaAdvisoryLock.integration.test.ts` |
| Generated exact-gap ordering/remaining/history invariants | `packages/common/test/gameClock.test.ts` |
Deployment and public-runtime evidence remain outside this audit and are still
open pending explicit user-test deployment authorization.
+36 -32
View File
@@ -13,39 +13,43 @@
관리자 감사는 [운영 안내](../play-audit-operations.md)에서 현재 기능을,
[설계](../design/play-audit.md)에서 요구사항과 배경을 확인합니다.
| 작업 | 문서 | 코드 시작점 |
| --------------------- | --------------------------------------------------------------- | ------------------------------ |
| 전체 구조 | [아키텍처 개요](../architecture/overview.md) | `app/`, `packages/`, `tools/` |
| process·worker·daemon | [런타임 아키텍처](../architecture/runtime.md) | app server와 CLI |
| profile·Gateway 배포 | [릴리스 운영 매뉴얼](../release-operations.md) | Admin GUI와 release-controller |
| 파일 위치 | [파일 지도](./code-map.md) | router, handler, schema |
| package 의존 방향 | [패키지와 파일 경계](../architecture/package-boundaries.md) | `packages/*`, `app/*` |
| 명령·전투·효과 | [도메인과 조립](./domain-and-classes.md) | `packages/logic` |
| mutation·flush | [요청·턴·저장](./request-turn-persistence.md) | game API, game engine |
| action module | [행동 모듈 프로토콜](../architecture/action-module-protocol.md) | `actionModules/` |
| ref 비교 | [차등 검증](../architecture/turn-state-differential-testing.md) | `tools/integration-tests` |
## 현재 구조와 구현 계약
[구조 문서 찾아보기](./reference-map.md)에는 시계·재시도·실시간 갱신·측정·운영 자료를
질문별로 모았습니다. 과거 계획과 현재 계약의 구분도 여기서 확인할 수 있습니다.
| 질문 | 문서 |
| --------------------------------------- | ------------------------------------------------------------------------------------------------------------------------------------------------------------ |
| 무엇이 어디서 실행되나요? | [개요](../architecture/overview.md), [런타임](../architecture/runtime.md) |
| 어느 파일부터 읽나요? | [파일 지도](./code-map.md), [패키지 경계](../architecture/package-boundaries.md) |
| 한 행동이 어떻게 계산되나요? | [도메인과 조립](./domain-and-classes.md), [행동 모듈](../architecture/action-module-protocol.md) |
| 언제 저장되고 실패는 어떻게 처리하나요? | [요청·턴·저장](./request-turn-persistence.md), [API 재시도](../architecture/api-input-event-replay.md) |
| 시간 정지·재개는 어떻게 되나요? | [게임 시계](../architecture/game-clock.md), [시간 도메인 목록](../architecture/time-domains.md), [재정렬 계약](../architecture/game-clock-reconciliation.md) |
| 설정을 여러 파일에서 조합하나요? | [시나리오 합성](../architecture/scenario-composition.md) |
| 화면에 변경이 어떻게 전달되나요? | [실시간 변경 원장](../architecture/realtime-change-journal.md) |
| 전투 시뮬레이터가 어디서 계산하나요? | [브라우저 Worker](../architecture/battle-simulator-browser-worker.md) |
| Ref와 무엇을 비교하나요? | [차등 검증](../architecture/turn-state-differential-testing.md) |
| TypeScript 버전이 왜 둘인가요? | [도구 체인 정책](../architecture/typescript-version.md) |
## 경계
## 변경 범위를 빠짐없이 확인하는 목록
- `packages/logic`은 계산과 규칙을 소유합니다.
- runtime I/O는 logic의 port를 app/infra adapter가 구현해 주입합니다.
- `app/game-engine`은 clock, queue, AI, 월간 순서, transaction과 flush를
소유합니다.
- `app/game-api`는 transport, 인증, input validation과 request acceptance를
소유합니다.
- `packages/infra`의 Prisma schema와 migration은 영속 구조의 기준입니다.
- `resources`는 scenario, map, unit set과 command profile을 구성합니다.
- actor와 resource owner는 session과 DB에서 서버가 결정합니다.
- `InputEvent`와 PostgreSQL transaction이 gameplay mutation의 내구성
경계입니다.
- Redis와 SSE는 session·worker·fan-out 경로이며 world commit의 대체 저장소가
아닙니다.
[엔진 호출 procedure 목록](../architecture/game-api-daemon-procedure-inventory.md)과
[직접 변경·journal 목록](../architecture/game-api-direct-mutation-journal-inventory.md)은
읽기 교재보다 변경 누락을 찾는 검토 자료입니다. 표의 조사 날짜·기준선과 현재
router·검사 코드를 함께 확인하세요. 새 API가 늘어도 과거 조사 숫자가 자동으로
현재 개수가 되지는 않습니다.
기능의 대응이 바뀌면 작업공간 루트 기준
`docs/ref-core2026-mapping.md`에 entry point,
호출 순서, 인증, DB mutation, RNG와 오류 경로를 갱신해 주세요.
공통 작업 규칙과 계약 분류는 제품 저장소 루트의 `AGENTS.md`를 따릅니다.
이 파일들은 핸드북 사이트 밖의 저장소 문서입니다.
시계 참여자 JSON·mutation evidence TSV는 기계가 사용하는 자료입니다. 형식과
검사 계약을 유지하며 해당 기능을 바꿀 때 갱신합니다.
## 측정·계획·운영 자료
| 자료 | 해석 범위 |
| ----------------------------------------------------------------------------------- | ----------------------------------------------------------- |
| [NPC 메모리 측정](../architecture/npc-lifecycle-memory-profile.md) | 지정 fixture의 메모리·생성/사망 부하. 운영 DB 처리량과 다름 |
| [NPC 천통 시간 측정](../architecture/npc-unification-timing-benchmark.md) | 인메모리 계산 시간. 실제 배포 성능 보장이 아님 |
| [시계 복구](./game-clock-recovery.md) | 상태·원장 확인과 같은 작업 재시도 |
| [릴리스 운영](../release-operations.md) | 실제 배포 작업과 준비 확인 |
| [관리자 콘솔](../admin-console.md), [플레이 감사 운영](../play-audit-operations.md) | 관리자 권한과 현재 조사 기능 |
| [테스트 정책](../testing-policy.md) | 실행 준비·검증 종류·skip의 해석 |
| [프론트엔드 CSS 구조](../frontend-css-architecture.md) | 화면 스타일의 소유권과 배치 계약 |
기능 설계의 목표, 코드에 있는 구현, 테스트로 확인한 범위, 실제 배포 상태는 서로
다릅니다. 문서의 “완료”는 함께 적힌 날짜와 검증 범위로 해석하세요.
-47
View File
@@ -1,47 +0,0 @@
# 구조 문서 찾아보기
[기초 안내](./first-steps.md)와 [경험자 안내](./system-walkthrough.md)가 학습 경로를,
아래 문서들은 세부 계약을 제공합니다. 목록·벤치마크·과거 계획을 처음부터 모두
읽기보다 현재 질문에 해당하는 문서를 고르세요.
## 현재 구조와 구현 계약
| 질문 | 문서 |
| --------------------------------------- | ------------------------------------------------------------------------------------------------------------------------------------------------------------ |
| 무엇이 어디서 실행되나요? | [개요](../architecture/overview.md), [런타임](../architecture/runtime.md) |
| 어느 파일부터 읽나요? | [파일 지도](./code-map.md), [패키지 경계](../architecture/package-boundaries.md) |
| 한 행동이 어떻게 계산되나요? | [도메인과 조립](./domain-and-classes.md), [행동 모듈](../architecture/action-module-protocol.md) |
| 언제 저장되고 실패는 어떻게 처리하나요? | [요청·턴·저장](./request-turn-persistence.md), [API 재시도](../architecture/api-input-event-replay.md) |
| 시간 정지·재개는 어떻게 되나요? | [게임 시계](../architecture/game-clock.md), [시간 도메인 목록](../architecture/time-domains.md), [재정렬 계약](../architecture/game-clock-reconciliation.md) |
| 설정을 여러 파일에서 조합하나요? | [시나리오 합성](../architecture/scenario-composition.md) |
| 화면에 변경이 어떻게 전달되나요? | [실시간 변경 원장](../architecture/realtime-change-journal.md) |
| 전투 시뮬레이터가 어디서 계산하나요? | [브라우저 Worker](../architecture/battle-simulator-browser-worker.md) |
| Ref와 무엇을 비교하나요? | [차등 검증](../architecture/turn-state-differential-testing.md) |
| TypeScript 버전이 왜 둘인가요? | [도구 체인 정책](../architecture/typescript-version.md) |
## 변경 범위를 빠짐없이 확인하는 목록
[엔진 호출 procedure 목록](../architecture/game-api-daemon-procedure-inventory.md)과
[직접 변경·journal 목록](../architecture/game-api-direct-mutation-journal-inventory.md)은
읽기 교재보다 변경 누락을 찾는 검토 자료입니다. 표의 조사 날짜·기준선과 현재
router·검사 코드를 함께 확인하세요. 새 API가 늘어도 과거 조사 숫자가 자동으로
현재 개수가 되지는 않습니다.
시계 참여자 JSON·mutation evidence TSV는 기계가 사용하는 자료입니다. 형식과
검사 계약을 유지하며 해당 기능을 바꿀 때 갱신합니다.
## 측정·계획·운영 자료
| 자료 | 해석 범위 |
| ----------------------------------------------------------------------------------- | ----------------------------------------------------------- |
| [NPC 메모리 측정](../architecture/npc-lifecycle-memory-profile.md) | 지정 fixture의 메모리·생성/사망 부하. 운영 DB 처리량과 다름 |
| [NPC 천통 시간 측정](../architecture/npc-unification-timing-benchmark.md) | 인메모리 계산 시간. 실제 배포 성능 보장이 아님 |
| [시계 구현 계획 기록](./game-clock-reconciliation-plan.md) | 당시 branch의 milestone. 현재 운영 상태의 기준이 아님 |
| [시계 복구](./game-clock-recovery.md) | 상태·원장 확인과 같은 작업 재시도 |
| [릴리스 운영](../release-operations.md) | 실제 배포 작업과 준비 확인 |
| [관리자 콘솔](../admin-console.md), [플레이 감사 운영](../play-audit-operations.md) | 관리자 권한과 현재 조사 기능 |
| [테스트 정책](../testing-policy.md) | 실행 준비·검증 종류·skip의 해석 |
| [프론트엔드 CSS 구조](../frontend-css-architecture.md) | 화면 스타일의 소유권과 배치 계약 |
기능 설계의 목표, 코드에 있는 구현, 테스트로 확인한 범위, 실제 배포 상태는 서로
다릅니다. 문서의 “완료”는 함께 적힌 날짜와 검증 범위로 해석하세요.