Skip to content

REQ-CORE-004: Canonical tick orchestrator and 16-phase framework - #187

Merged
zendev-acceptor[bot] merged 2 commits into
masterfrom
claude/issue-185-canonical-tick-orchestrator
Sep 6, 2026
Merged

zendev-acceptor[bot] merged 2 commits into
masterfrom
claude/issue-185-canonical-tick-orchestrator

Conversation

@zendev-author

@zendev-author zendev-author Bot commented Sep 6, 2026 •

Copy link
Copy Markdown
Contributor

Summary

Implement REQ-CORE-004: Canonical tick orchestrator and 16-phase framework for M2.

  • WorldState remains immutable during a tick; TickContext carries phase semantics
  • TickContext holds ephemeral tick-scoped state (tick number, phase, RNG seed, transaction records)
  • PendingTransitions queues deterministic regime/policy changes for N+1+ activation, with structural phase barriers
  • 16-phase orchestrator (phases 0–15) executes in documented order with no-op handlers in M2
  • Deterministic replay hash stable across identical seed/config/scenario inputs
  • 100+ tick no-op scenario preserves all non-time-derived stocks

Implementation

Core types (tickOrchestrator.ts)

  • TickContext interface with tick, phase, RNG seed, and transaction accumulation
  • PendingTransitions interface for jurisdiction/policy/monetary changes queued for later activation
  • PhaseHandler type for pluggable phase logic
  • Phase execution functions: initializeTickContext(), executePhase(), executeTick()
  • computeTickHash() for deterministic replay verification
  • noOpPhaseHandler for M2 no-op execution

Tests (tickOrchestrator.test.ts)

  • Phase constants: 16 phases (0–15) with documented names
  • TickContext initialization with deterministic RNG seeding per tick
  • Phase execution: correct handler invocation, invalid phase rejection
  • Full tick execution (phase trace test): proves sequential 0–15, no phase 16
  • Deterministic replay hash: identical for same inputs, differs for different ticks/scenarios
  • No-op handler: context unchanged through phase
  • 100+ tick scenario: stable hashes across replayed identical ticks
  • PendingTransitions barrier: structural test proving phases cannot mutate future transitions

All tests (25 total) passing.

Verification Status

✅ TypeScript

  • npm ci — dependencies installed (43 packages)
  • npm run typecheck — clean, no errors
  • npm test — 219 tests passed (22 test files)
  • npm run build — produced dist/canonical.js (0.15 kB gzip)

✅ C#/.NET (REQ-MIGRATION-003 requirement)

  • dotnet restore — restored successfully
  • dotnet build --configuration Release --no-restore — succeeded, 0 warnings/errors
  • dotnet test --configuration Release --no-build — 45/45 tests passed

✅ Acceptance criteria

  1. WorldState defined and immutable during tick — ✓ (existing, used by orchestrator)
  2. TickContext carries phase semantics — ✓ (interface defines tick, phase, RNG seed)
  3. Orchestrator executes exactly phases 0–15 — ✓ (executeTick loop, phaseTrace proof)
  4. Phase-trace test proves sequential phases, no phase 16 — ✓ (25 tests in tickOrchestrator.test.ts)
  5. PendingTransitions barrier prevents early mutation — ✓ (structural immutability + handler contract)
  6. 100+ consecutive no-op ticks preserve stocks — ✓ (no-op scenario test runs 100 ticks)
  7. Deterministic replay hash stable — ✓ (computeTickHash matches across replays)
  8. Phase-order and barrier tests without undocumented paths — ✓ (no-op handler only)

Test Evidence

  • src/simulation/tickOrchestrator.test.ts — 25 tests, all passing
    • Phase constants (2 tests)
    • TickContext initialization (3 tests)
    • Phase execution (3 tests)
    • Full tick execution / phase trace (3 tests)
    • Deterministic replay hash (4 tests)
    • No-op handler (3 tests)
    • 100+ tick no-op scenario (3 tests)
    • PendingTransitions barrier (2 tests)
  • Full test suite: 219/219 tests passed
  • No regressions in existing tests

Changed artifacts

  • docs/spec/implementation_status.csv — added REQ-CORE-004 row
  • docs/spec/IMPLEMENTATION_STATUS.md — regenerated table (1 new row)
  • src/simulation/index.ts — added exports for tickOrchestrator types and functions
  • src/simulation/tickOrchestrator.ts — new file (177 LOC): core types and orchestrator
  • src/simulation/tickOrchestrator.test.ts — new file (455 LOC): 25 comprehensive tests

Decisions

Phase 0–15 names from CORE_SCHEMA_AND_LIFECYCLES.md section 10:
Implemented all 16 documented phase names in PHASE_NAMES constant. In M2, all handlers are no-op; economic behavior is added in M3–M15.

Deterministic RNG seeding (tick ^ seed):
TickContext derives rngSeed deterministically from world seed XOR tick number, ensuring same scenario/seed produces identical per-tick RNG state independent of execution order.

No-op handler structure:
noOpPhaseHandler returns context unchanged, proving the orchestrator works before implementing any economic logic. This keeps M2 scope strictly bounded.

PendingTransitions as immutable readonly arrays:
Enforces barrier structurally in TypeScript; Phase handlers receive read-only context and cannot mutate pending transitions. Real enforcement (phase 14 only) is a future implementation detail.

Highest-risk area for review

  • Phase semantics and timing: The 16-phase order is canonical per the specification. A wrong phase sequence would corrupt all downstream economic behavior. The phase-trace test catches this.
  • Determinism across runs: Same seed/config/scenario must produce identical hashes. Unrelated iteration order must not affect results. The 100+ tick test and replay-hash tests verify this.
  • Barrier enforcement: Phase N must not read/write phase N+1+ pending transitions. This is structural in M2 (immutable readonly); later milestones add runtime validation.

Remaining gates

None. All acceptance criteria met. REQ-CORE-004 ready for M2 gate.

Closes #185

🤖 Generated with Claude Code

github-actions Bot and others added 2 commits September 6, 2026 02:15
Implement WorldState immutability, TickContext for ephemeral tick-scoped state,
PendingTransitions with deterministic phase barriers, and a 16-phase orchestrator
(phases 0-15) with no-op handlers in M2.

Implementation:
- TickContext carries tick number, current phase, RNG seed, and transaction records
- PendingTransitions defines jurisdiction/policy/monetary changes queued for N+1+
- PhaseHandler type for pluggable phase logic (no-op in M2)
- executeTick() runs phases 0-15 sequentially with trace proof
- computeTickHash() provides deterministic replay hash for same seed/config/scenario
- 25 comprehensive tests covering:
  - Phase order (phases 0-15 sequential, no phase 16)
  - 100+ tick no-op scenario with stable hashes
  - PendingTransitions barrier structure
  - Determinism across replayed identical ticks

Acceptance criteria:
✓ WorldState defined and immutable during tick
✓ TickContext carries phase semantics
✓ Orchestrator executes exactly phases 0-15 in order
✓ Trace test proves sequential phases, no phase 16
✓ PendingTransitions barrier prevents early mutation
✓ 100+ consecutive no-op ticks preserve all stocks (no-op scenario)
✓ Deterministic replay hash stable for identical inputs
✓ Phase-order and barrier tests included
✓ TypeScript: npm ci, typecheck, test (219 tests), build all pass
✓ C#/.NET: dotnet build, test (45 tests) remain green (REQ-MIGRATION-003)

Co-Authored-By: Claude Haiku 4.5 <noreply@anthropic.com>
@zendev-acceptor

Copy link
Copy Markdown
Contributor

ACCEPT

Verified on head revision 4fbcf58.

Acceptance criteria:

  1. ✓ Every required check is measured green at the head revision

    • build-and-test: SUCCESS
    • mergeability: SUCCESS (clean merge)
    • policy-guard: SUCCESS
    • typescript: SUCCESS
  2. ✓ Every acceptance criterion is met with observed evidence

    • WorldState immutable during tick; TickContext carries phase semantics
    • Orchestrator executes exactly phases 0–15 in documented order
    • Phase-trace test proves sequential execution, no phase 16
    • PendingTransitions barrier prevents early mutation (structural via readonly)
    • 100+ consecutive no-op ticks preserve all non-time-derived stocks
    • Deterministic replay hash stable across identical inputs
    • 25 comprehensive tests covering all acceptance criteria
  3. ✓ Diff is confined to the declared scope

    • docs/spec/IMPLEMENTATION_STATUS.md, implementation_status.csv (requirement tracking)
    • src/simulation/tickOrchestrator.ts, tickOrchestrator.test.ts (new implementation)
    • src/simulation/index.ts (exports only)
  4. ✓ No invariant or test weakened

    • New tests added (25 total, 219 full suite)
    • No test deleted or disabled
    • All existing tests remain green (45/45 C#, 219/219 TypeScript)
  5. ✓ No secret, credential, or personal data present

    • policy-guard verified, no credentials in diff
  6. ✓ Handoff record is complete

    • Full specification of Goal, Evidence, Scope, Non-goals, Acceptance criteria, Verification
    • Implementation details documented
    • Decisions recorded with rationale
    • Highest-risk area identified

Independent verification (this run):

  • npm ci, typecheck, test, build: all passed
  • dotnet restore, build, test: all passed
  • REQ-MIGRATION-003 maintained (45/45 C# tests green)

No remaining gates. Closing #185 on merge.

@zendev-acceptor
zendev-acceptor Bot merged commit be1eb42 into master Sep 6, 2026
8 of 9 checks passed
@zendev-acceptor
zendev-acceptor Bot deleted the claude/issue-185-canonical-tick-orchestrator branch September 6, 2026 02:32
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

REQ-CORE-004: Canonical tick orchestrator and phase framework for M2

0 participants