Phase 13 plan — Backend + Android (incremental parallel)
Phase 13 plan
Living plan. Updated at each sub-phase boundary. Detail concentrates on the next 5 dispatchable steps; later steps are skeletal placeholders re-planned as the phase progresses.
1. Phase 13 in one paragraph
Phase 13 grows the backend (NestJS local-tunnel test deployment per ADR-0006) and a Kotlin Android client (sibling repo walkrpg-mobile, D-008 §2, D-015) together. Backend endpoints ship as Android needs them; Android features ship as the backend can serve them. There is no sharp “backend done” gate — Phase 13 ends when the Android client has the feature set the closed-beta cohort needs to play the vertical slice end-to-end. The canonical exit scenario: an Android user installs the app, signs in (mock auth), creates a Walker with a class, completes onboarding, ingests a synthetic walk, sees energy update, opens Quest 001 in Plenny, completes a quest step, receives tree points, allocates a node on cluster.first-steps, opens the faction screen and sees Unfinished Guild reputation update, walks into a Quest-002 encounter, resolves combat via the simulator API, syncs state back to backend, kills the app, reopens it, and finds the same state on the server. When that scenario passes end-to-end on a real Android device against the local-tunnel backend, Phase 13 is done and Phase 14 (VPS migration) opens.
2. Parallelism rule
Lore work runs in parallel with Phase 13. narrative-designer continues authoring Plenny Quest 003, additional regional NPCs, regional lore deepening, faction-specific quest hooks, and the foundation.mdx D-012/D-013 tie-in passage — all independently of Phase 13 dispatch.
Does NOT block Phase 13:
- Adding new NPCs (data layer, already validated by Zod schemas).
- Authoring new quests beyond 001/002 (data layer; backend endpoints are quest-id-agnostic).
- Authoring region lore prose (wiki PL, no schema or backend touch).
- Authoring class instances (data layer; class-pick endpoint reads from data).
- Mechanics-designer authoring more tree nodes / keystones in
data/.
DOES block Phase 13 increments:
- Open D-level decisions in §4 — specifically the progression system spec (D-016 candidate). Until that ratifies, sub-phases that touch XP, level, or point-award math cannot dispatch.
- Class instance scope: at least 1 playable class instance authored before the class-pick onboarding sub-phase dispatches (currently 0; schema exists, no instances).
Dispatch independence: narrative-designer is dispatched by CEO directly (or via game-director routing) for lore increments; tech-architect + mobile-developer are dispatched paired for Phase 13 increments. The two streams share the data layer (read-only from Phase 13’s side — Phase 13 does not modify quest/faction/region/NPC instances, only consumes them).
3. Three areas of Phase 13
3.1 Combat
Forward-references (added 2026-05-22 re-check): D-018 ratifies combat as the premium Energy sink (~30% per fight of a nominal 5k-step day); current 13-7 backend honours the Energy debit on
/combat/encounterinitiation. D-020 ratifies pull-based trigger + tieredtropypool + visible-before-commit risk choice — these are post-Phase-13 forward-references (§10.3 below). D-010 governs HP=0 non-punitive defeat; D-020’shard/keystone-readyenergy-loss tail is orthogonal to D-010 §3.
Exists: Canonical math (combat/formulas.md §1-12), 19-stat dictionary (12 combat-resident + 7 tree-resident-only), seeded PRNG (xorshift32, D-010 §1), combat simulator (data/src/sim/combat.ts, commit 8856366) with worked-example reproducibility, Walker-first alternation (D-010 §2), non-punitive defeat (D-010 §3), cold_resist tagged-damage handling (12b-2).
Missing: Any backend surface (no /combat/encounter endpoints), any Android surface (no combat UI implementation — the 11e-1 wireframe exists but no code), encounter trigger plumbing (quest beat / region event → encounter spin-up), encounter outcome wiring (encounter result → quest state delta + tree-point award + faction-rep delta).
Phase 13 must deliver: A backend endpoint that initializes an encounter from a quest beat (returns seed + both stat snapshots), an endpoint that records a turn (Walker submits action, server replays simulator with stored seed up to that turn, returns next state), an encounter-end endpoint that resolves outcome to quest/tree/rep deltas. Android UI rendering the turn loop, energy spend animation, hp bars, retreat affordance. Must reproduce simulator’s worked-example deterministically across client and server (seeded replay is the anti-cheat foundation — even in mock-trust ADR-0006 posture, the contract is designed-in now to avoid retro-fitting later).
3.2 Quests
Forward-references (added 2026-05-22 re-check): D-024 ratifies the canonical 6 × 18 = 108 quest distribution (15 main + 3 hidden per region, strict per-region linear chain, Plenny canonical first). Phase 13 ships 6 Plenny quests (1 hidden = Quest 005) — D-024-compliant, but only ~33% of Plenny’s required 18-quest saga. Remaining Plenny + 5 other-region sagas are post-Phase-13 narrative-designer work. See §10.7.
Exists: Quest 001 (Plenny opening, phase 5b), Quest 002 (Frostlands, “Pieczętarnia milczy”, phase 11a-3), POST /quest/start + POST /quest/complete endpoints (11d-1, with 422 repeatable-guard), QuestSchema with steps/rewards/prerequisites, quest-log UI wireframe (11e-2).
Missing: Step-level progress (start/complete are quest-level; no per-step granularity yet), quest discovery (which quests are visible to a walker at any point — currently no GET /quest/available or equivalent), the D-006 Pillar 3 cosmos hook (allocating a keystone unlocks a hidden quest — designed but no implementation), quest-trigger combat plumbing (Quest 002 implies an encounter, but the trigger→encounter path is not built), Android quest log UI implementation (wireframe exists, no code), quest-prerequisite evaluation (quest A done → quest B visible).
Phase 13 must deliver: GET /quest/available returning per-walker visible quests evaluated against prerequisites + faction-rep gates + keystone gates, per-step progress endpoints (POST /quest/:id/step/:n/advance), keystone-unlock-as-quest-reveal hook (when POST /tree/allocate allocates a keystone, append any quests it unlocks to the available set), Android quest log + quest detail screens implementing 11e-2 wireframe, quest start/complete buttons wired to backend, quest-progress notifications.
3.3 Character progression
Forward-references (added 2026-05-22 re-check): D-019 ratifies 5 canonical classes (one per faction) + starting-cluster differentiation. Phase 13-3 ships
class.cartographer+cluster.first-steps; the four remaining classes + clusters (32 nodes + 4 keystones) landed at data layer on 2026-05-22 (c6c722e/06d75b5/83b5451) but are NOT surfaced on Android — backend adapter mirror tracked atops/escalations.mdQ8 FYI; mobile class-pick screen still bundles Cartographer only. §4.2 below should be read as CLOSED by D-019. See §10.2.
Exists: Walker profile (GET /walker/profile), tree state (GET /tree/state), tree allocation (POST /tree/allocate), cluster.first-steps with ~20 Plenny nodes + 1 keystone (Krok Niezachwiany), faction reputation read/write endpoints (11d-1, 11d-2), ClassSchema (no class instances authored), AscendancySchema (no instances).
Missing: Level concept (Walker has no level field — walker/profile exposes whatever the schema carries, but level is not defined; D-006 implies progression depth but the math is unratified), XP gain semantics (where do tree points come from numerically? D-006 Pillar 3 says ~70% quest grants + ~30% keystone unlocks, but the per-quest grant table is not ratified), point-award rules (does completing a step grant N points? Does a quest grant a flat M? Does a region-completion bonus exist?), class instances (schema exists, zero playable classes authored), class-pick flow (onboarding wireframe shows it; data + endpoint + UI not implemented), Walker bootstrap (registration → class pick → faction induction → first-quest dispatch is a designed flow but not implemented end-to-end), the player-facing Level UI element (not in any wireframe — defining what it surfaces is part of the progression spec).
Phase 13 must deliver: The progression system spec (D-016 candidate, see §4 below) ratified BEFORE any sub-phase touching XP/level/point math dispatches. After ratification: walker/profile extended with progression fields (level, xp, tree-points-banked, tree-points-spent), point-award endpoint or in-line side-effects on quest-complete + keystone-allocate, at least 1 class instance authored in data/, POST /walker/create (or equivalent) accepting class id, Android class-pick screen, Android Walker home displaying level + xp + points-banked, Android tree viewer allocation flow integrated with point-banking.
4. Open decisions (must answer before related sub-phases dispatch)
Three open decisions block Phase 13 sub-phases. They are ordered by blocking severity.
4.1 Progression system spec (D-016 — RATIFIED 2026-05-20)
Status: CLOSED. D-016 ratified — Model A (emergent level, walker.level = walker.tree_points_spent) + keystone bonus = 1pt + deliberate ~20% inaccessibility gap. ~108 quests × 1pt + ~36 keystones × 1pt bonus = ~144 pts across ~180 nodes. ~75/25 split (D-006 §Pillar 3 amended from ~70/30). Home surface: single Poziom N number + banked banner. See D-016 for full spec.
Historical context (pre-ratification): D-006 Pillar 3 ratified the informal ~70/30 quest/keystone split but left the surrounding system unratified — no canonical Walker level concept, no XP curve, no per-quest point-award table, no level-cap, no level-gate semantics on tree allocation. The progression system was the connective tissue between Pillar 1 (Steps = Energy), Pillar 2 (Passive Tree), and Pillar 3 (Quest↔Tree loop), blocking every progression-touching sub-phase until ratified.
Who decides: CEO + game-director + mechanics-designer. narrative-designer consulted for quest-grant flavour. ui-designer consulted for what the player surface displays.
Where ratified: D-level (canonical). /decide flow. Adds D-016 to canon.
Framing questions CEO will need to answer (proposed for /research progression-system):
- Does Walker have a
levelinteger, or is “level” emergent fromtree_points_spent? (PoE has both — character level and passive points; some walking-RPGs collapse the two. Collapse simplifies UI; separation enables level-gated content independent of allocation choices.) - Tree points per quest — flat or scaled? (Flat: every quest grants
Npoints. Scaled: points scale with quest tier / region depth / step count. Flat is simpler to balance against the ~150-200 node target tree; scaled matches “harder quests give more.”) - Tree points per keystone unlock — same as quest grant or different? (D-006 says ~30% from keystones at full game; with 6 leak-handler keystones + further keystones authored over time, this implies keystones grant bigger lumps than regular quests. Need a ratio.)
- Tree-point cap / level-cap interaction. With ~150-200 nodes and 70/30 split, total quest+keystone count at full game has to mathematically reach point parity. What is the target node count vs. point count? (PoE 1 is ~120 points across ~1300 nodes; Last Epoch is ~110 across ~1100 nodes; ours is ~150-200 across ~150-200 — much denser, almost 1:1.)
- What does the player see on Home regarding progression? (Just points-banked + tree-points-spent? Or a level number? Or a quest-progress bar to next point grant? This shapes the home wireframe revision.)
4.2 Class instance scope for Phase 13 — CLOSED by D-019
Status: CLOSED (2026-05-22). D-019 ratifies the canonical 5-class roster (one per faction; Cartographer / Pieczetarz / Pielgrzym / Komiwojazer / Tropiciel). The W-level “ship 1, defer rest” pick at 13-3 has executed: Cartographer plays on Android in Phase 13; the other four are authored at data layer (commits c6c722e / 06d75b5 / 83b5451, 2026-05-22) including 4 starting clusters (first-seal / first-lantern / first-route / first-sign, 32 nodes + 4 keystones). Backend adapter mirror for the 4 new classes is pending (intentional Phase 13 scope, tracked at ops/escalations.md Q8 FYI). Mobile bundle still ships Cartographer only — surfacing the other 4 on Android is forward-referenced to D-027 onboarding diegetic expansion (§10.10) or post-Phase-13.
Historical context (pre-D-019): ClassSchema and AscendancySchema existed (commit 04f1a71), but zero class instances were authored. Onboarding wireframe showed class-pick. Cannot ship Android class-pick UI against an empty class roster.
Who decides: mechanics-designer proposes; CEO ratifies if D-level (i.e., if it changes the canonical class list). If just “for Phase 13 closed-beta cohort, ship the 1-class subset of the eventual N-class roster,” it is W-level (mechanics-designer autonomous).
Where ratified: Likely W-level — pick 1 class to author first (most natural fit: a Cech-aligned cartographer starting in Plenny, since cluster.first-steps and Quest 001 are Plenny-bound). If CEO wants to define the FULL class roster up-front (e.g. “the canonical list is these 6 classes, one per region”), it becomes D-level.
Proposed framing: CEO confirms whether (a) ship 1 class for Phase 13 + author rest later as W-level, OR (b) ratify the canonical N-class list now as D-level.
4.3 Combat-encounter API surface shape
Why open: D-010 ratifies combat resolution philosophy; combat/formulas.md ratifies math. Neither ratifies the API surface (request/response shapes, encounter-state persistence model, replay vs. live-step semantics). tech-architect will draft this as an ADR (likely ADR-0008 — but ADR-0007 is reserved for Phase 14 VPS migration, so this is ADR-0008+ to avoid number clash, or the numbering re-flows).
Who decides: tech-architect drafts; mechanics-designer cross-reviews against formulas.md; system-reviewer cross-checks pre-canon; CEO ratifies if D-level. Most likely B-level (backend architecture, not gameplay canon) unless a question arises that affects the simulator contract.
Where ratified: B-level (ADR in wiki/src/content/docs/tech/adr/). Drafted at the sub-phase where combat encounter endpoints land (currently skeletal sub-phase 13-7). ADR number = next free at draft time (ADR-0007 was re-allocated to Android network layer in sub-phase 13-1; VPS migration ADR defers to ADR-0008+ at Phase 14 trigger; combat encounter ADR fills the next slot when 13-7 dispatches).
Proposed framing: Sub-phase 13-7 (combat encounter API ADR) produces the answer; this is not a separate /research.
5. Feature checklist (Phase 13 completeness contract)
Comprehensive enumeration of every feature that MUST exist when Phase 13 ships. Tagged per area. Items pulled from D-006/D-007/D-008/D-009/D-010/D-011/D-014, the data schemas, the existing backend endpoint inventory, and the UI wireframe inventory. Each item gets a checkbox.
Backend (NestJS, local-tunnel test, ADR-0006 posture)
-
POST /auth/callbackretained as-is (mock auth, ADR-0006). -
GET /walker/profileextended with progression fields (level/xp/points-banked/points-spent — pending D-016). -
POST /walker/create(or equivalent) — accepts class id, faction starting allegiance (if any), creates Walker with default stats from class. -
POST /step/ingestretained (mock-trust per ADR-0006), wired to update energy + streak. -
GET /walker/streak— current streak day count + recognition tier (per D-007: +20% at 7d, +50% at 30d). -
POST /quest/startretained. -
POST /quest/completeretained. -
POST /quest/:id/step/:n/advance— per-step progress. -
GET /quest/available— list of quests visible to this Walker right now, evaluated against prerequisites + rep gates + keystone gates. -
GET /tree/stateretained. -
POST /tree/allocateretained, extended to emit keystone-unlock side effects (reveal hidden quests). -
GET /faction-repretained. -
POST /faction-rep/deltaretained. -
POST /combat/encounter— initialize encounter from quest beat. Returns seed + initial stat snapshots. -
POST /combat/encounter/:id/turn— submit Walker action; server replays simulator with stored seed; returns next state. -
POST /combat/encounter/:id/resolve— encounter ends (win/retreat/defeat); emits quest/tree/rep deltas. -
POST /combat/encounter/:id/retreat— Walker retreats mid-encounter (D-010 §1 encounter exit condition). - Prisma schema migrations for all new tables (encounter, encounter-turns, walker-class-allegiance, progression fields).
- Swagger docs current for all endpoints.
- Test suite green (>= current 103/103 + new endpoint coverage).
- CORS configured for Android local-tunnel access.
- Mock-auth bearer token flow documented in
tech/api/.
Mobile (Kotlin Android, sibling repo walkrpg-mobile)
- Repo bootstrap: Android Studio project, Kotlin, Jetpack Compose, Hilt or Koin DI, Retrofit + kotlinx-serialization, Room (offline cache).
- Build pipeline: GitLab CI for
walkrpg-mobile(build + lint on push; release builds manual). - Splash + mock auth screen (per onboarding wireframe).
- Walker creation flow: class pick screen (renders authored class instances).
- Tutorial overlay (per onboarding wireframe).
- First-walk prompt (per onboarding wireframe).
- Home screen: region card, streak ribbon, quest pill, faction strip, bottom nav (5 tabs per D-014 §1: Home / Tree / Factions / Quests / Craft — Craft tab is stub-only in Phase 13).
- Tree viewer: cluster.first-steps rendering, mastery popover, keystone lock state, allocation flow with point-banked check, a11y focus order (matches wireframe).
- Post-walk sync screen: step delta, energy delta, streak update, quest progress (matches wireframe).
- Quest log: row titles use
name.enper D-011, prose usesname.pl. - Quest detail screen.
- Faction screen: 5 factions, rep tiers, visible per-region.
- Combat screen: matches 11e-1 wireframe, renders turn loop, energy spend, hp bars, retreat affordance.
- Crafting tab stub: placeholder “Coming in Phase X” (full crafting UI is post-Phase-13 per D-015 — Phase 13 ships Android core loop without full crafting).
- Health Connect integration: read step count, push to
/step/ingest(mock-trust validation server-side). - Offline cache: 7-day offline cap per D-009 §2; queued actions sync on reconnect.
- Provisional-allocation UI affordance per D-009 §2 (allocations made offline render as provisional until server confirms).
- Bilingual UI: EN/PL switch, defaults to system locale, all
LocalizedStringconsumers respect locale. - System chrome consistency: notifications + push use
name.enper D-011. - a11y: 200% font scale, screen reader, focus order — per wireframe a11y notes.
- Color tokens implemented: 6 region tokens + neutral + state + faction (per design-system).
- Typography: Literata (display) + Inter (UI) loaded.
Data layer
- At least 1 class instance authored (
data/src/content/classes/), aligned to Plenny start. - At least 1 ascendancy per authored class (or none, if mechanics-designer defers ascendancies to Phase 13+).
- Progression curve constants (if D-016 introduces an XP curve) live in
data/src/schemas/progression.tsanddata/src/content/progression/. - No regressions on existing 17 typed instances.
Cross-cutting
- Auto-commit policy honored on every Phase 13 sub-phase commit.
- Roadmap updated per sub-phase ship.
- This plan (phase-13-plan.md) updated per sub-phase ship.
- Language policy (
pnpm lint:language) green. - Tag policy (
pnpm lint:tags) green. - D-016 (progression system) ratified before sub-phases that depend on it dispatch.
Exit scenario (the ultimate checklist)
- On a real Android device: install APK from CI artifact.
- Sign in via mock auth.
- Pick a class (the 1 authored class).
- Complete onboarding tutorial.
- Trigger a synthetic step ingest (or take a real walk if Health Connect data is available).
- See energy increase, streak update.
- Open Quest 001, complete first step.
- Receive tree points, see them banked on home.
- Open tree viewer, allocate a node on
cluster.first-steps. - Verify allocation persisted to backend (kill app, reopen — node stays allocated).
- Open faction screen, see Unfinished Guild reputation reflect a quest reward.
- Open Quest 002, walk into combat trigger.
- Resolve combat encounter (win, retreat, or defeat — at least one outcome path tested end-to-end).
- Encounter outcome reflected in quest state on server side.
- Kill app, reopen — all state persists.
When every checkbox above is green, Phase 13 ships and Phase 14 (VPS migration) opens.
6. Sub-phase decomposition
Detail concentrates on the next 5 sub-phases. Later sub-phases are skeletal placeholders. Each detailed sub-phase ends with: prerequisite (which open decision must close first if any), scope, deliverables, leads, estimated cost, dependencies.
Detail-planned (first 5)
13-1 — Android repo bootstrap + walker/profile read
Prerequisite: None. Unblocked.
Scope: Stand up the walkrpg-mobile sibling repo (Android Studio project, Kotlin, Compose, Retrofit, Hilt). Build a minimal app that signs in via mock POST /auth/callback, fetches GET /walker/profile against the local-tunnel backend, and renders the response on a placeholder home screen. No UI polish, no domain features — pure plumbing.
Deliverables: walkrpg-mobile repo initialized on GitLab; Android Studio project compiles + runs on emulator; mock auth flow works against ADR-0006 local-tunnel backend; one screen renders Walker profile JSON; basic CI pipeline (build + lint on push). Documents the mock-auth handshake in walkrpg-mobile/README.md (English).
Leads: tech-architect (network layer + auth contract) + mobile-developer (repo bootstrap + Compose scaffold) paired.
Estimated cost: 1 dispatch session. Roughly equivalent to phase 8b in scope.
Dependencies: None. Unblocks 13-2 (anything mobile after this needs the repo).
Status: DONE — 2026-05-20. Commits: e260ead (ADR-0007 Android network layer, this repo) + walkrpg-mobile sibling repo 8931019 (repo metadata rewrite Flutter→Kotlin), 5ebb89b (gradle + version catalog), 0f982b0 (Hilt + Retrofit + auth interceptor + token store), 7e66a62 (MainActivity + HomeScreen rendering /walker/profile). ADR-0007 re-allocated to Android network layer (ADR-0006 originally reserved 0007 for VPS migration; VPS ADR defers to next-free at Phase 14 trigger — see §4.3). Backend follow-ups added (HttpExceptionFilter, X-Request-Id middleware, CORS bootstrap) — tracked in ADR-0007 §Backend deliverables, to be picked up when backend-engineer dispatches.
13-2 — Progression system spec (D-016 /research + /decide)
Prerequisite: None (this IS the prerequisite for downstream sub-phases).
Scope: Run /research progression-system per §4.1 framing questions. game-director + mechanics-designer cross-write candidate progression models. system-reviewer cross-checks against D-006/D-007. CEO /decide ratifies as D-016. No code, no data instances — pure design + canon write.
Deliverables: Research artifact at ops/research/progression-system.md; D-016 landed as wiki/src/content/docs/canon/decisions/D-016-progression-system-model-a-tuned-keystone-bonus-20-inaccessi.md; progression curve / point-award math drafted into wiki/src/content/docs/tree/progression.md (or equivalent) at status:draft, ratified to status:canon after D-016. Open Plenny quest 001/002 point-award values back-filled to match.
Leads: game-director (orchestrates) + mechanics-designer (proposes math) + narrative-designer (quest-grant flavour). CEO ratifies.
Estimated cost: 1 research session (3-5 question pass, max 3 rounds) + 1 /decide session.
Dependencies: Unblocks 13-3 (walker creation needs to know what level means), 13-5 (tree-point grant needs to know how many points per quest), and any future progression UI sub-phase.
Status: DONE — D-016 ratified 2026-05-20. Research artifact at ops/research/progression-system.md. game-director orchestrated mechanics-designer + narrative-designer in parallel. CEO /decide selected option (B): Model A + keystone bonus = 1pt + deliberate ~20% inaccessibility gap. Final spec: 108 quests × 1pt + 36 keystones × 1pt bonus = ~144 pts across ~180 nodes, ~80% reach, ~75/25 quest/keystone split. D-006 §Pillar 3 wording amended from ~70/30 → ~75/25. Home shows single Poziom N + banked banner. Unblocks sub-phases 13-3, 13-5, 13-10. See D-016 for full spec.
13-3 — Walker creation + class pick (1 class authored)
Prerequisite: D-016 ratified (13-2 done). Resolves §4.2 open decision (will most likely pick 1-class W-level).
Scope: Author 1 class instance in data/src/content/classes/ (Plenny-aligned cartographer is the natural fit). Add POST /walker/create endpoint to backend. Build Android class-pick screen + walker-creation flow per onboarding wireframe. Default starting Walker writes to backend, returns via GET /walker/profile with progression fields populated per D-016.
Deliverables: 1 class instance in data/; backend POST /walker/create + Prisma migration; Android class-pick screen + walker-creation flow; bilingual class name/description rendering. Updated tests on backend (>= +5 cases).
Leads: mechanics-designer (class instance authoring) + tech-architect (backend endpoint + schema migration) + mobile-developer (Android UI) — three-lead paired dispatch.
Estimated cost: 1 dispatch session (heavier than 13-1, lighter than 13-5).
Dependencies: Blocked on 13-2 (D-016). Unblocks 13-4 (home screen needs a Walker to display).
Status: DONE — 2026-05-20. Three-lead paired dispatch shipped:
- mechanics-designer:
class.cartographerinstance authored (bdf9f51,data/src/content/classes/cartographer.ts, bilingual PL/EN, Plenny start, Cech-aligned via region); Quest 001 + 002 reward retrofitted to flat 1pt per D-016 (9304f10, was 4pt / 6pt);wiki/src/content/docs/tree/progression.mddrafted at status:draft (7a5ec02, headline math + ~20% gap worked example + D-013 endgame cross-ref + banner copy). Walker schema NOT in data layer — confirmed backend-only (Prisma owns Walker). - tech-architect: Chose option (b)
POST /walker/class(preserves ADR-0006/auth/callbackauto-create contract); Prisma migration (a476ec8) dropswalkers.level, renamesavailablePoints→treePointsBanked, addstreePointsSpent(default 0) +classId(TEXT nullable), backfillstreePointsSpentfrom existing TreeAllocation/KeystoneAllocation; endpoint + DTO + service + tests (0b6eba7); API contract docs (089294c). Test count 103 → 141 (unit 102→111, e2e 24→30). Idempotent on same-classId re-pick, 409 on different-classId re-pick (no respec in Phase 13). - mobile-developer:
ClassPickScreen.kt+WalkerCreationViewModel+AppNavigation.ktNavHost (LOADING → CLASS_PICK → HOME); hardcodedBUNDLED_CLASSESin Kotlin for the 1 cartographer (TODO refactor to bundled JSON orGET /class/listwhen N > 1); bilingual rendering viaLocalConfiguration.current.locales; test count 5 → 21 (+16). Initial commitsce9bcc4,3744951,a17f588. Reconciliation pass1672561aligned endpoint/walker/create→/walker/class+ DTO field renames (availablePoints removed, treePointsBanked/treePointsSpent/classId added, level kept on wire as computed view) per tech-architect’s option (b) choice. versionName bumped to0.1.0-13-3.
Wire-level D-016 deviation flagged (B-level follow-up): level: Int field stays on wire as server-computed view (= treePointsSpent); D-016 strict reading says emergent only (client-side compute). Either accept as wire convenience (current state) or drop wire field + amend ADR-0007 §2 in a future sub-phase. No blocker.
ADR-0007 §2 amendment needed (W-level follow-up): Kotlin DTO field set documented in ADR-0007 §2 is from 13-1 (pre-D-016 rename). Add a follow-up amendment to record the renamed wire shape so iOS port (Phase 15) inherits correctly.
D-019 reconciliation (added 2026-05-22 re-check): 13-3’s “1 class for Phase 13” framing is now subsumed by D-019 — canonical roster = 5 classes one-per-faction; data layer now carries all 5 (Cartographer + Pieczetarz + Pielgrzym + Komiwojazer + Tropiciel, commits c6c722e / 06d75b5 / 83b5451). 13-3 backend + mobile surfaces still serve Cartographer only — the other 4 surface on Android post-Phase-13 (or per D-027 onboarding expansion if scheduled). Backend adapter mirror for the 4 new classes pending; see ops/escalations.md Q8 FYI.
13-4 — Android home screen + step ingest + streak
Prerequisite: 13-3 done (Walker exists with class + progression state).
Scope: Build the Android home screen per wireframe (region card, streak ribbon, quest pill, faction strip, 5-tab bottom nav with Craft as stub). Wire Health Connect read; push step counts to POST /step/ingest; render energy + streak deltas. Add GET /walker/streak to backend (currently streak is implicit in profile; surface it explicitly per D-007 attestation invariant). Post-walk sync screen ships in this sub-phase too (it is the home screen’s natural sibling).
Deliverables: Android home screen + post-walk sync screen; Health Connect integration; GET /walker/streak endpoint; streak math wired to D-007 per-day attestation invariant (decay on missed attested day, NOT missed sync day). a11y pass: 200% font scale, screen reader focus order.
Leads: tech-architect (streak endpoint + Health Connect contract) + mobile-developer (Compose home + sync screens + Health Connect plumbing) paired. ui-designer consulted only if wireframe deviation needed.
Estimated cost: 1 dispatch session — likely the biggest sub-phase so far (home screen is dense per the 11e-2 + 9 wireframes).
Dependencies: Blocked on 13-3. Unblocks 13-5 (quest log lives in bottom nav).
Status: DONE — 2026-05-20. 4-thread parallel dispatch shipped (Thread A core 13-4 + ui-designer wireframe pass + Thread D ADR-0007 backend deliverables):
- tech-architect:
GET /walker/streakendpoint (currentStreakDays + recognitionTier + multiplier 1.0/1.2/1.5 + lastAttestedDay; commitec74aed);wiki/src/content/docs/tech/api/health-connect-contract.mdxdrafted (10 sections: provenance + sampling window + per-day aggregation + extended /step/ingest body + 4-guard mock-trust posture + permission flow + debug fallback + iOS HealthKit inheritance + production deferred + open follow-ups; commite825290). Minimal Prisma migration20260520120000_streak_longest_lengthaddedStreakState.longestLengthDays. Test count +14 (12 unit + 2 e2e). - mobile-developer: HomeScreen full rewrite (region card + ProgressionCard per D-016 with pisarska linijka LinearProgressIndicator + streak ribbon + quest pill + faction strip + 5-tab bottom nav incl. Craft stub), PostWalkSyncScreen, Health Connect integration (HealthConnectReader + DayStepBucket + SyncStateStore EncryptedSharedPreferences + 7-day client cap per D-009 §2), 14 new bilingual strings, 8 a11y items verified. Test count 21 → 50 (+29). versionName 0.1.0-13-3 → 0.1.0-13-4. walkrpg-mobile commits
f922aef,05a832a,cceaad9,88b70b1,cbc0b9d. - ui-designer (wireframe pass): home-screen.mdx amended — new
## Progression card detail (D-016)section + extended primary ASCII sketch + day-0 sketch + 88dp dimension table row + a11y screen-reader subsection + streak ribbon D-007 backend field-name alignment note. post-walk-sync.mdx amended — D-016 grant callout copy (+1 Tree Point banked./Linijka oddana do składu. Spis przyjął.) replacing pre-D-016+4 tree pointsplaceholder + new## Tree point grant callout — standalone spec (D-016)section + states matrix grant callout column. pisarska linijka concrete recommendation: vertical ruled line 3dp×64dp left-aligned, three tick marks at 50/100/150 of 180 nodes, fill =--color-region-plenny70% opacity. Commitfad3f5a(orchestrator-committed after 2-line lint fix on frontmatter description PL chars). - Thread D backend-engineer (ADR-0007 §Backend deliverables — parallel non-13-4): HttpExceptionFilter (normalize error envelope, NestJS exception → ADR-0007 error codes mapping; commit
cfbc450); RequestIdMiddleware (X-Request-Id generate/echo + Pino-ready log context but currently standard NestJS Logger; commitc82d293); CORS bootstrap (env CORS_ALLOWED_ORIGINS, defaultlocalhost:3000,10.0.2.2:3000; commit8f7efc6); ADR-0007 §Backend deliverables marked “shipped” with SHAs (commitcea5e41). Test count +14 (8 filter + 6 middleware). Pre-existing prisma client drift fixed viaprisma generate. One deviation: implementedcredentials: trueper dispatch brief vs ADR-0007 §10credentials: false— functionally identical for Bearer-token flows; flagged for tech-architect.
Combined test count delta: 141 (start) → 183 (end). Backend +42 (tech-architect 14 + backend-engineer 28 incl. baseline 123→137). Mobile 21 → 50.
Wire-level field reminder: level: Int stays on wire as server-computed view of treePointsSpent (deviation from D-016 strict reading flagged in 13-3, unchanged in 13-4).
ADR-0007 §2 amendment outstanding (W-level follow-up): still pending refresh for D-016 Kotlin DTO field rename. iOS port (Phase 15) inherits.
B-level CORS credentials note: backend-engineer implemented credentials: true; ADR-0007 §10 says false. Reconcile in B-level decision or amend ADR-0007 §10 to true.
13-5 — Quest log + Quest 001 end-to-end + first tree allocation
(Cross-ref 2026-05-22: QuestGateEvaluator from this sub-phase is the canonical implementation of D-024 §2 hidden-quest gating. KEYSTONE_GATE + FACTION_REP_GATE + REGION_GATE all activate the per-region linear chain + off-spine hidden semantics. Phase 13’s 6 Plenny quests represent ~33% of D-024’s per-region 18-quest saga; remainder is post-Phase-13 narrative-designer work.)
Prerequisite: 13-4 done (home + step ingest working) + D-016 ratified (point-award math known).
Scope: Android quest log screen + quest detail screen per 11e-2 wireframe. Wire GET /quest/available (new endpoint), POST /quest/start, POST /quest/:id/step/:n/advance (new endpoint), POST /quest/complete. Tree allocation flow on Android: tap node, confirm, send POST /tree/allocate, show provisional-vs-confirmed state per D-009. End-to-end: walk → ingest → start Quest 001 → advance step → complete → receive tree points → allocate node on cluster.first-steps → state persists across app restart.
Deliverables: Android quest log + detail screens; backend GET /quest/available + POST /quest/:id/step/:n/advance; tree allocation UI integrated with points-banked check; provisional-allocation visual state on Android; offline queue (Room) for quest/allocation actions when offline (7-day cap per D-009).
Leads: tech-architect (new quest endpoints + prerequisite/gate evaluator) + mobile-developer (quest screens + tree allocation flow + offline queue) + mechanics-designer (consulted for point-award values per D-016) paired.
Estimated cost: 1 dispatch session — likely the second-biggest sub-phase. The quest↔tree loop closes here in user-visible form for the first time.
Dependencies: Blocked on 13-4 + D-016. Unblocks downstream combat work (13-6+) by establishing the quest-state pattern combat-encounter must hook into.
Status: DONE — 2026-05-20 (all 4 threads landed).
tech-architect (backend):
04a0122—feat(backend): GET /quest/available + POST /quest/:id/step/:n/advance + gate evaluator (sub-phase 13-5)—/quest/availablereturns{available[], hiddenCount, evaluatorVersion};/quest/:id/step/:n/advancestrict-order 1-indexed, final step does NOT auto-complete (D-016 — explicit /quest/complete required for +1pt); QuestGateEvaluator pure synchronous collect-all (PREREQUISITE active, REGION_GATE active, KEYSTONE_GATE schema-active + adapter-pending, FACTION_REP_GATE schema-active + adapter-pending); /tree/allocate provisional field already present (returns false always per ADR-0006 mock-trust).c57a674—docs(tech): quest-available + quest-step-advance API contracts (sub-phase 13-5)— API contract pages drafted at status:draft.- Backend tests 183 → 210 (+27). Adapter follow-up (B-level, < 50 LOC): mirror
keystoneRequirement+factionRepRequirementfrom schemas tobackend/src/common/game-content.tsQuest interface so KEYSTONE_GATE + FACTION_REP_GATE activate on real quest content.
mechanics-designer (data):
8f40e35—feat(data): QuestSchema gate evaluator fields + per-step beats (sub-phase 13-5)— added optionalQuestStepSchema.beats(factionRep + loreUnlock per-step),QuestSchema.factionRepRequirement({factionId, minTier:int 0..5}),QuestSchema.keystoneRequirement({keystoneId}). regionRequirement deferred — existingregionIdserves with comment-expanded semantics (“Walker’s last attested region matches regionId → in-region”).6e247e0—feat(data): Quest 001/002 per-step beats (factionRep + loreUnlock per D-016)— Quest 001 5 steps with Cech-rep + lore-unlock beats (no tree points per step); Quest 002 4 steps with beats + step 5 outcome-branch placeholder. cluster.first-steps connectivity verified: entry nodenode.even-strideallocatable on 0 prior allocations;keystone.unshaken-step(Krok Niezachwiany) unlocked by Quest 001 with atomic allocate + 1pt bonus = effectively 2 progression points per Quest 001.
mobile-developer (Android): walkrpg-mobile commits:
fad0a9a—feat(13-5): QuestLogScreen + QuestDetailScreen + filtering + quest start/advance/complete flow— QuestLogScreen (filter chips All/Active/Completed, LazyColumn, QuestCards, hidden quest slots per Pillar 3, pull-to-refresh, D-011 bilingual names), QuestDetailScreen (hero block, step timeline, Start/Advance/Complete buttons, D-016 reward callout), QuestLogViewModel + QuestDetailViewModel (@HiltViewModel, offline enqueue on network failure, 409 idempotent, SharedFlow events), QuestApi, QuestDto, ApiException, QuestRepository/Impl.ae65874—feat(13-5): TreeViewerScreen + allocation flow + provisional state per D-009— TreeViewerScreen (pannable/zoomable canvas 0.3–3× scale, cluster.first-steps nodes, four visual states, keystone diamond composable + D-014 screen-reader label “Keystone — special”), AllocationConfirmDialog, points-banked pill in TopAppBar, TreeViewerViewModel (tap→confirm→POST, client-side banked-points guard, provisional optimistic state per D-009 §2 mock-trust, provisional restored from offline queue on load), TreeApi, TreeDto, TreeRepository/Impl.63480ae—feat(13-5): Room offline queue + WorkManager + 7-day cap per D-009 §2— OfflineAction @Entity (offline_actions table v1), OfflineActionDao, OfflineQueueDb (exportSchema=true), OfflineQueueRepository + OfflineQueueRepositoryImpl @Singleton, OfflineQueueWorker @HiltWorker (FIFO drain, 7-day cap, QUEST_ADVANCE/QUEST_COMPLETE/TREE_ALLOCATE, 409 idempotent, Result.retry on failure), OfflineQueueModule (15-min periodic worker, KEEP, CONNECTED constraint), WalkrpgApp implements Configuration.Provider with HiltWorkerFactory.23b388b—feat(13-5): nav extension + bilingual strings (quest + tree + offline)— AppNavigation: QUEST_LOG, QUEST_DETAIL/{questId}, TREE_VIEWER routes; HomeScreen: onNavigateToQuestLog + onNavigateToTree callbacks wired to bottom nav tabs and QuestPill.onTap; 23 new EN + 23 PL string keys (quest log filter chips, status labels, action buttons, tree viewer labels, offline queue badge) — all D-011 compliant.6f60a6e—test(13-5): QuestLog + QuestDetail + TreeViewer + OfflineQueue tests— 38 new tests: QuestLogViewModelTest (7), QuestDetailViewModelTest (8), TreeViewerViewModelTest (8), OfflineQueueRepositoryTest (8), OfflineQueueWorkerTest (7, Robolectric). Total: 50 → 88.e394a23—chore(13-5): bump versionName + WorkManager/Hilt-Work/Robolectric deps— versionName 0.1.0-13-4 → 0.1.0-13-5; libs.versions.toml + build.gradle.kts updated.
API contract posture: Mobile designed against expected GET /quest/available + POST /quest/:id/step/:n/advance shapes; tech-architect’s actual landed shapes match closely. Field-level reconciliation, if any drift surfaces in integration testing, is a single QuestDto.kt update.
Offline provisional note: Provisional node IDs survive process death by being reconstructed from offlineQueue.getAll() TREE_ALLOCATE payloads on each load() call — no additional persistence needed.
Lore parallel (Thread C — narrative-designer):
df17a2b—feat(data): Plenny Quest 003 — dzwoniacy-magazyn (leverages plenny.md forward hooks)— Quest 003Dzwoniący magazyn(Bell-ringing storeroom): Drukarnia Cechu leak-ink mystery fused with plenny.md magazyn nr 17 reservation. 5 steps, prereqquest.001-first-road, 1pt reward per D-016. Forward hook (pine-resin smell + ink-colour question) seeds long-arc Pan Korytarz signature-forensics thread.021eb09—feat(data): npc Pan Bezelec — night warden of Trzecie Biuro magazyn nr 17— Pan Bezelec carded (Cech, Plenny, nocnystrażnik).- B-level canon assertion: “leak-paper hushes its own scent” (Plenny archiwum wyciekowe property) — region-internal, no D-level conflict.
Combined test count deltas this sub-phase:
- Backend: 183 → 210 (+27).
- Android: 50 → 88 (+38, 5 new test files via Robolectric).
- versionName: 0.1.0-13-4 → 0.1.0-13-5.
Open follow-up (W/B-level, dispatched separately, NOT blockers for 13-6):
- B-level (tech-architect): mirror
keystoneRequirement+factionRepRequirementfromdata/src/schemas/quest.tstobackend/src/common/game-content.tsQuest interface (< 50 LOC) — activates KEYSTONE_GATE + FACTION_REP_GATE evaluators on real quest content. - W-level (tech-architect): ADR-0007 §2 amendment for D-016 Kotlin DTO rename — carried from 13-3/13-4. iOS port (Phase 15) inherits.
- B-level (mechanics-designer + narrative-designer): lore-unlock id dereference — currently free-form slug; mobile shows placeholder. Lore-library subsystem post-Phase-13.
- B-level (mobile-developer): per-step beat callout UI shape — D-016 banner pattern for
Cech +3/Lore unlocked: <slug>rows. Currently no per-step callout rendered. - B-level (mobile-developer + tech-architect): Quest 002 step 5 outcome-branch (A/B/C Akademia/Bractwo/Cech lean) — placeholder on
rewards.reputationpending 11c-2 outcome-branching schema.
Skeletal (placeholders, re-planned as Phase 13 progresses)
One-liners, just so the shape is visible. Re-planned at each /work session boundary.
- 13-6 — Faction screen + faction-rep visible on Android. DONE 2026-05-20. mobile-developer (single-lead): FactionsScreen + FactionDetailScreen + BUNDLED_FACTIONS (5 hardcoded, mirrors BUNDLED_CLASSES pattern from 13-3), FactionRepository (getFactions/getFactionRep/getMergedFactions), 5-tier ladder with current highlighted, filter chip All/This-Region, GET /faction-rep read-only (POST /faction-rep/delta intentionally not wired — quest deltas flow through quest.service per D-007). Test count 88 → 116 (+28). versionName 0.1.0-13-5 → 0.1.0-13-6. walkrpg-mobile commits
bb7e654,2e5cc69,d3cf758,fa68cd0. Parallel (13-7 prep): tech-architect drafted ADR-0008 combat encounter API (358b123) — 10 sections, encounter lifecycle, 4-endpoint family, simulator integration as hard rule (backend imports@walkrpg/datasim, no re-implementation), 9 iOS port inheritance items + 4 platform-specific changes, 6 open questions deferred to 13-7 implementation. Parallel (B-level follow-up): backend-engineer mirroredkeystoneRequirement+factionRepRequirementtobackend/src/common/game-content.tsQuest interface (014cc6a) — activates KEYSTONE_GATE + FACTION_REP_GATE evaluators on real quest content (still pass-through since no quest sets fields yet); also caught quest-003 missing from adapter array drift. +2 backend tests (210 → 212). Lore parallel (Thread C): narrative-designer authored Plenny Quest 004Połowa rejestru(8a6ae87, 5 steps, prereq quest.003-dzwoniacy-magazyn, half-bisected-ledger trace continues Quest 003 pine-resin forward hook, Pan Korytarz identity stays at poziom 25+ reservation) + new NPCWnęt Sosnowy-Półwieksmolarz (d6cf0bd). Forward hook for Quest 005+: other half of smolarnia ledger in Targosie OR Academy private cabinet — Walker doesn’t know which. Orchestrator fixed Polish-quote-pair syntax errors (narrative-designer used„...„+ ASCII close — replaced with proper„...„U+201D) before commit. - 13-7 — Combat encounter API + Quest 002 trigger plumbing. DONE 2026-05-20. (Cross-ref 2026-05-22: implements D-020 encounter resolution surface. D-020 §2 pull-based pool + §3 badge taxonomy + §4 visible-before-commit risk choice are forward-references — currently only quest-beat-driven encounters fire; step-driven
tropyaccumulation is post-Phase-13. D-018 ~30%-per-fight Energy sink already honoured.) Paired: mechanics-designer (data layer) + backend-engineer (impl). Mechanics step 1 (b8847e5,d461894) resolved ADR-0008 §8.1 + §8.6:data/src/schemas/opponent.ts(Zod, bilingual, 8-stat block bit-identical toEnemySnapshot),data/src/content/opponents/frost-thing-slow-vent.ts(canonical numbers hp=18, dmg=7, def=2, acc=0.65, eva=0.05, crit=0.02, crit_mult=1.5),QuestStepBeatSchemamigrated todiscriminatedUnion("kind", [narrative, encounter])— all 13 existing beats across Quest 001/002/004 explicitly migrated tokind: "narrative". Quest 002 step 3 rewritten asbeat-3-frost-thing-at-the-slow-ventwith encounter beat referencingopponent.frost-thing-slow-vent, factionRep + loreUnlock carried through on the encounter beat. W-level dropped the standalonekind: "factionRep"variant the brief suggested — narrative beats already carry factionRep[] inline (ops/decisions/2026-05-20-13-7-mechanics-discriminated-beats.md). ADR-0008 flipped Proposed→Accepted (97a2041). Backend step 2 (cf4e6ab,a7a4c67,f992f3a) ships: Prismacombat_encounterstable (inline JSONBreplayLog,combat_turnsdeferred per §8.4),EncounterState/EncounterOutcomeenums, Walker reverse relation;backend/src/common/game-content.tsadapter mirror for opponents +QuestStepBeatunion (mirror pattern same as014cc6akeystone/faction mirror); fullbackend/src/combat/NestJS module (service + controller + DTOs + errors) with all 4 endpoints (POST /combat/encounter,/turn,/resolve,/retreat), Bearer auth, ADR-0007 envelope, 8 error codes per §5. Simulator-as-hard-import honored — backend importssimulateEncounter/makePrngfrom@walkrpg/data/sim; NO re-implementation of combat math. Replay strategy:simulateEncounterslice withretreatPolicy: neverper W-level (ops/decisions/2026-05-20-13-7-backend-replay-strategy.md). Seed:crypto.randomInt(0, 0x100000000)(ops/decisions/2026-05-20-13-7-backend-seed-generation.md). D-016 separation surfaced on the wire:treePointsDelta: 0literal on/resolveresponse; encounter does NOT grant tree points. D-010 non-punitive enforced: defeat clamps hp to 1, no XP/rep/streak loss.QuestService.advanceStepgained an optionaltxparam +QuestModuleexportsQuestServicefor cross-module injection. Tests: +42 incombat.service.spec.ts(169 → 211 backend). All lints clean. Deferred to 13-9 (NOT regressions): tree-modifier stat composition for walker snapshot (Phase 13 uses base class stats only),walker.hpcolumn persistence (currentlyvoid finalWalkerHp— hp lives only in encounter snapshot until column lands). Deferred to Phase 14+: abandoned-state cleanup worker,COMBAT_REPLAY_MODEenv var for production-strict replay rejection,combat_turnstable if turn-level analytics emerge. - 13-8 — Combat UI on Android. DONE 2026-05-20. mobile-developer (single-lead): full Compose
CombatScreenper wireframe 11e-1 with 6 UI states (Idle / Initializing / Active / PendingResolve / PendingRetreat / Resolved / Retreated / Error). 4-endpoint RetrofitCombatApi+ DTOs against ADR-0008 §3.CombatRepository+CombatViewModel— server-canonical state (next-expectedturnIndexfrom server response, never client-side counter). Nav routecombat/{questId}/{stepIndex}/{opponentTemplateId}wired fromQuestDetailScreenwhen active step beatkind === "encounter". Action set: Attack + Retreat per ADR-0008 §8.3 + wireframe 11e-1 §4.1 (Defend / Use-Energy-Burst not stubbed — no dead UI). Auto-resolve on PendingResolve viaLaunchedEffect(uiState)— player already tapped Attack on the winning turn; requiring a second Continue tap was poor UX. Retreat =AlertDialog(wireframe’s 2-sec auto-dismiss chip dropped per W-level — recomposition-timer interaction). No client-side simulator prediction in 13-8 — per-turn spinner during server roundtrip; Kotlin xorshift32 re-impl deferred to 13-9 or post-13. Opponent name derived from slug (“opponent.frost-thing-slow-vent” → “Frost-thing”) — temporary, proper endpoint deferred. Bilingual strings + 8+ a11y items (live regions on turn outcomes, content descriptions). versionName 0.1.0-13-6 → 0.1.0-13-8 (skipped 13-7, backend-only). +53 Android tests (116 → 169):CombatRepositoryTest(18),CombatViewModelTest(14),CombatWorkedExampleTest(7 — formulas.md §10 replay byte-for-byte against seed 92 fixture),CombatScreenTest(14 pure-logic). walkrpg-mobile commits4831d49,77092ce,f54aa7a,cb57928,b7fbcf0. W-level log:ops/decisions/2026-05-20-13-8-combat-ui-android-w-level.md. - 13-9 — Combat outcome → quest/tree/rep deltas. DONE 2026-05-20. tech-architect scope memo → mechanics-designer (data layer) → backend-engineer (impl) → mobile-developer (Kotlin port + UI) chain. Tech-architect step 1 (
384b562): cross-cutting design memowiki/.../tech/phase-13-9-design.md(392 lines, four deliverables with current-state / target-state / contracts / open-questions). 3 W-locks ratified by CEO before downstream dispatch — (1)walker.currentHpisInt?nullable (NULL = never initialized, derives to compose’d hp_max on read; cheapest backfill, no double-write); (2)composeWalkerStatslives indata/src/sim/compose.tsNOT in backend (iOS Phase-15 port inherits via ADR-0008 §6); (3) /resolve enrichment is FULL —walkerProgressionalways-zero block surfaces the D-016 invariant structurally on every encounter resolve. Mechanics step 2 (eb14862):composeWalkerStatspure function — sorted-id traversal for byte-stable order-independence, per-node add-then-mul bucketing, throws on unknown node ids.ClassSchemaextended to full 10-field combatStats block (snake_case mirrors simulator’sWalkerSnapshotshape) — replacesbaseHp/baseEnergy(deleted, no deprecation aliases — single source of truth).NodeSchemagains optionalcombatModifiersarray (typed add/mul ops on stat enum); free-formmodifierspreserved for step-economy. Cartographer combatStats: hp 80, energy 120, dmg 10, def 4, acc 0.82, eva 0.08, crit 0.05, critMult 1.5, energy_cost_per_action 1, cold_resist 0. Phase 13 passthrough — no nodes carry combatModifiers yet. +15 unit tests (14 → 29 data package). Backend step 3 (3bb9fe0): Prismaadd_walker_current_hpmigration (current_hp INTEGERnullable, no backfill — NULL is intended pre-13-9 state, first encounter resolve writes value).game-content.tsadapter mirror: Class withcombatStatsblock, NEWNodeinterface + mirror array, cartographer literal verbatim from data content.buildWalkerSnapshotrewritten async — fetches tree allocations, callscomposeWalkerStats(classData, allocatedIds, nodeRegistry), substituteswalker.currentHpclamped to hp_max per §1.2.resolveEncounter+retreatEncounterpersistcurrentHpinside their$transactionblocks (D-010 defeat=1 clamp honored on write; retreat persists final hp; victory persists final hp; idempotent re-resolve returns reputationBefore/After=0 since pre-tx state unrecoverable per §3.4).Resolve/RetreatEncounterResponseDto enriched:walkerProgressionall-zero block (D-016 invariant — future regression catchestreePointsBankedDelta !== 0immediately);factionRepDeltaswithreputationBefore/reputationAfter/tierBefore/tierAfter;encounterSummary.walkerHpStart+walkerHpDeltafor animation;loreUnlocked[];questStateAfter.previousStepIndex.FactionRepService.applyDeltaextended to return before/after/tier triple.GET /walker/profilereturnscurrentHp+currentHpMax(both non-null on wire, currentHp resolves NULL → derived hp_max). +25 backend tests (211 → 236). Mobile step 4 — walkrpg-mobile 3 commits:7ce5d91(sim — bit-identical KotlinXorshift32port:Int.ushrmaps JS>>>, seed-0 remaps to 1 per frozen contract;CombatMathprediction-only subset withpredictAttackTurn; draw-order discipline miss=1 roll / hit=3 rolls),fd75fe9(features —CombatViewModelSavedStateHandle constructor +computePrediction()+handleTurnResult()reconciliation +resyncPrngFromServerRolls()(nulls PRNG on mismatch); spinner removed; nonextPrngStateon wire — handled via draw-count advance reconciliation (documented in mobile decision log); enrichedCombatDto+CombatDomaintypes with all new fields;CombatRepositoryImplmaps enrichment fields;WalkerProfile.currentHp+currentHpMax;CombatScreenHpDeltaBar (500ms animateFloatAsState), TierPromotionBadge (AnimatedVisibility/fadeIn), LoreUnlockChip — all with contentDescription + liveRegion=Polite;WalkerHpHudon HomeScreen with color-coded HP bar; +5 bilingual strings; versionName 0.1.0-13-8 → 0.1.0-13-9),17da80c(tests — 169 → 218 (+49):Xorshift32Test(7 — draws 9-18 corrected from wrong placeholder values to verified node.js output, would have failed at CI on draw 9 without the fix);CombatMathTest(12);CombatPredictionTest(8);CombatDtoTest(14 — backward-compat with pre-13-9 backend shape verified);CombatRepositoryTest(+3 enrichment mapping + D-016 invariant);CombatViewModelTest(SavedStateHandle plumbed, accuracy fixture 0.80→0.82);HomeViewModelTest(+3 HP HUD);CombatWorkedExampleTestalready correct (accuracy 0.82 + new fields). W-level decisions underops/decisions/2026-05-20-13-9-*(4 logs: tech-design-memo, mechanics-compose-walker-stats, backend-implementation, mobile delivery). Combined test counts post-13-9: backend 236 (211 → 236, +25); data package 29 (14 → 29, +15); Android 218 (169 → 218, +49). Deferred to later sub-phases (not regressions): haptics on crit/victory/defeat (13-8 deferred, still open); opponent localized name endpoint (13-8 deferred, still open); wiki/api/reference docs for combat + walker-profile endpoints (nowiki/.../api/directory exists yet — backend-engineer flagged, future docs sub-task should createcombat-encounter.mdx+walker-profile.mdx); explicit progression delta endpoints (encounter/resolvedeliberately shows zero progression deltas per D-016 — actual XP/level/treePoints flow through other endpoints when D-016 banking ratio fires). - 13-10 — Keystone-unlock-as-quest-reveal (D-006 Pillar 3 cosmos hook). DONE 2026-05-20. (Cross-ref 2026-05-22: Quest 005
niemilknacy-kurieris the first hidden quest withkeystoneRequirement— fully D-024 §2 compliant. The cosmos-hook UX surfaces D-006 Pillar 3 + D-024 hidden-discovery in user-visible form for the first time.) narrative-designer + mobile-developer parallel, then backend-engineer integration test. All KEYSTONE_GATE plumbing already lived since 13-5 (quest-gate-evaluator.service.ts+hiddenCountin /quest/available); 13-10 lands the first content + Android UX + e2e proof. Narrative (351a7de,e0fc772): Quest 005quest.005-niemilknacy-kurier(Niemilknący kurier/ “The Unhushed Courier”) — first quest withkeystoneRequirement: { keystoneId: "keystone.unshaken-step" }. Five-beat companion-walk in Plenny with new NPCnpc.stary-marno-niedoczas(Stary Marno Niedoczas — kurier of a courier-house dissolved 112 years ago, no idle rest since). Premise diegetically literalizes the keystone’s removal of idle regen: only a Walker with Krok Niezachwiany can hold Marno’s stride. Faction-rep:faction.unfinished-guild(+4 beats 1+3),faction.wild-path(+2 beat 4) — first Dziki Trakt accrual in a Plenny quest. Forward hook (Quest 006+ reservation): Marno carries sealed envelope of his own dissolved house — same house-mark as Quest 004 pinewood slip (npc.pine-half-century) — but addressee identity stays unresolved. Pan Korytarz poziom-25+ reservation strictly preserved. NPC slug renamed mid-flight (old-marno-out-of-time→stary-marno-niedoczas) for lint compliance + convention withbrodek-spozniony/pan-bezelec. Mobile — walkrpg-mobile 4 commits:2663044(QuestRefreshBus singleton SharedFlow withextraBufferCapacity = 1to survive tab-switch timing — chosen over caller-driven option per W-level log;QuestRepository.refresh()interface method; TreeViewerViewModel injects bus + signals on successful keystone allocation; QuestLogViewModel subscribes in init + delta-detects newly-unlocked quest ids;acknowledgeNewlyUnlocked()+ filter preservation),b833aaf(D-006 cosmos hook UX: Snackbar with action label “Open Quest Log” /Otwórz dziennikon TreeViewer withonNavigateToQuestscallback,HiddenCountHintcomposable at bottom of QuestLog withliveRegion = LiveRegionMode.Politefor screen-reader announcement, 5 EN + 5 PL strings, Polish plural via template string — full<plurals>resource deferred to translator UX pass),b0c01e6(+29 tests above the +12-18 target: QuestRefreshBus, delta detection, hiddenCount, a11y, filter preservation, offline-failure silent-preserve path per D-009 heavy-offline posture, Polish plural correctness, content-description assembly; 218 → 247),190d9e0(versionName 0.1.0-13-9 → 0.1.0-13-10, versionCode 2 → 3). Backend (a0a0f59): integration tests + adapter-mirror gap-fill. Quest 004 (quest.004-polowa-rejestru) was missing frombackend/src/common/game-content.tsquests array (silent gap — no test referenced it pre-13-10; adding Quest 005 without 004 would have made all keystone-specific tests vacuously pass since the prereq gate would never resolve). Both added verbatim-aligned with data layer; Quest 005 is the first entry to setkeystoneRequirement, activating KEYSTONE_GATE on real content. Stale 13-5 comment “No keystoneRequirement / factionRepRequirement set in data layer yet” removed. +4 quest.service.spec.ts tests indescribe("GET /quest/available — keystone-gated reveal (13-10)"): hide-when-keystone-missing, reveal-when-both-gates-pass, hide-when-prereq-missing-even-with-keystone, hiddenCount-decreases-by-exactly-1 transition proof. Backend 236 → 240. W-level logs:ops/decisions/2026-05-20-quest-005-niemilknacy-kurier.md(narrative — 6 decisions including quest-premise choice from 3 candidates, NPC new-vs-reuse, faction-rep recipients, forward hook framing, quest type discriminator, slug shape) +ops/decisions/2026-05-20-13-10-mobile-quest-unlock-arch.md(mobile — 5 decisions including bus-vs-caller-driven, snackbar-vs-chip notification, Polish plural strategy, hiddenCount placement, offline silent-preserve). Combined test counts post-13-10: backend 240 (+4); data 29 unchanged; Android 247 (+29). Deferred to later sub-phases (mobile-developer raised, defer-by-default in 13-10 — Phase 13-10 owns minimum reveal flow, polish lands elsewhere): haptic on new-quest unlock per wireframe §4.4 “heavy impact + discovery tone” (haptic infra not wired in Phase 13 anywhere);onNavigateToQuestscallback wiring into nav graph (next nav-increment sub-phase); bus signal scope remains keystone-only (regular node allocations don’t flip quest gates by current game logic; revisit if backend evaluator evolves). - 13-11 — Bilingual UI polish + a11y full pass. DONE 2026-05-20. ui-designer + mobile-developer sequential. UI step 1 (
1b94be6): acceptance matrixwiki/.../ui/phase-13-11-acceptance.md(290 lines, ENG, 7 sections). W-lock: Settings screen for EN/PL switcher placement (gear icon on Home top-bar; SegmentedButton;walkrpg.locale.overrideSharedPreferences key; CompositionLocal-based zero-restart switching). Per-screen a11y checklist covering 9 implemented Android screens (Onboarding/ClassPick, Home, TreeViewer, QuestLog, QuestDetail, Factions, FactionDetail, CombatScreen, WalkerHpHud component). TalkBack + bilingual + 200% font-scale acceptance criteria. Test surface spec (+25-40 target). Explicit defer list: haptics, crafting, dark/light mode contrast audit, RTL, voice control. W-level log:ops/decisions/2026-05-20-13-11-ui-locale-switcher-placement.md. Mobile step 2 — walkrpg-mobile 4 commits:09431cb(Settings screen withSingleChoiceSegmentedButtonRowEN|PL + haptic-placeholder row +@Preview(fontScale=2f);LocaleStore.ktfactory pattern —create()for production EncryptedSharedPreferences,createForTest()for Robolectric unit tests;LocaleModule.ktHilt@Modulesingleton;LocaleProvider.ktLocalAppLocaleCompositionLocal +LocaleOverrideProvidercomposable wrappingLocalConfiguration+LocalContext;LocaleViewModel.kt@HiltViewModelwithStateFlow<String> localeTag;MainActivitywraps AppNavigation in LocaleOverrideProvider; AppNavigation gains SETTINGS route + HomeonNavigateToSettingscallback. Zero-restart mechanism: LocaleOverrideProvider rebuilds Configuration + locale-configured Context in the Compose tree; allstringResource()calls see locale-correct strings.xml on next recomposition. Chose Compose CompositionLocalProvider over AppCompatDelegate.setApplicationLocales —ops/decisions/2026-05-20-13-11-mobile-locale-propagation.md),e97ad13(a11y audit + font scale + bilingual fixes — HomeScreen settings gear contentDescription, WalkerHpHud health-state labelhealthy/warning/criticalderived from fraction; StreakRibbon liveRegion Polite; TreeViewer available-points counter liveRegion comment confirming no nav-re-entry spam; tab barfontScale >= 1.8ffalls back to icon-only with full label as icon contentDescription per ui-designer flag;@Preview(fontScale=2f)added to HomeScreen, SettingsScreen, Factions, FactionDetail, QuestLog, QuestDetail, PostWalkSync — no clip/truncate/overflow; ProgressionCard hardcoded"${level} / ${totalNodes} allocated"extracted toR.string.progression_allocatedwith EN%1$d / %2$d allocated+ PL%1$d / %2$d zaalokowane; Polish<plurals>resourcesquest_count+step_countwith all 5 formszero/one/few/many/otherupgrading from 13-10b833aaftemplate-string workaround),cbf21c3(+53 tests across 9 files:Phase1311A11yTest3,Phase1311FontScaleTest6 — Home Loaded/Loading/Error at 1.0+2.0,Phase1311ClassPickScreenFontScaleTest4,Phase1311QuestLogFontScaleTest4,Phase1311FactionFontScaleTest4,Phase1311CombatScreenA11yTest6 — structural assertions + documented checks,Phase1311LocaleTest7 — LocaleStore persistence + effectiveLocale logic withcreateForTest()bypass,Phase1311PluralsTest13 — PLquest_countN=0/1/2/5/21 +step_countN=0/1/3/7 + EN forms,Phase1311SettingsScreenTest6 — EN/PL segments visible + click callbacks + labels + haptic placeholder),1a4bd3b(versionName 0.1.0-13-10 → 0.1.0-13-11, versionCode 3 → 4). Combined test counts post-13-11: backend 240 unchanged; data 29 unchanged; Android 247 → 300 (+53). CAVEAT — Gradle verification deferred: mobile-developer authored 53 tests but could NOT execute./gradlew test/lint/buildin the sub-agent environment (no Gradle binary installed;gradlewwrapper JAR not committed pergradle-wrapper.properties— comment saysgradle wrapper --gradle-version 8.7bootstrap required). Tests are code-reviewed and follow established patterns from prior sub-phases (13-9/13-10 Compose-test conventions), but pass/fail status is unknown. Verification deferred to next session (run Gradle bootstrap +./gradlew test) or to CI image (mingc/android-build-box). Flag for next-session audit. Deferred from 13-11 (per acceptance matrix §7): haptic feedback infra (b833aaf+09431cbplaceholder row prepared), Crafting screen (Phase 14+), dark/light mode contrast audit, RTL support, voice control beyond TalkBack. - 13-12 — Offline queue hardening + 7-day cap enforcement. Walks done offline, allocations made offline, quest progress made offline — all sync correctly on reconnect. (Cross-ref 2026-05-22: D-018 §What-not-decide mandates sink-debit ordering be respected on sync — flag for QA. Optional scope absorption per §10.9 / §10.10: minimal D-026 FCM token registration + per-class opt-in surface AND/OR D-027 diegetic onboarding expansion (Bertranda walkthrough + 50-step register + Map first-impression + class-pick-as-beat-1-close). FLAG_LEAD: CEO triage at next planning round — does 13-12 absorb minimal D-026 push + D-027 diegetic onboarding, or do those defer to a new 13-N+1 / post-Phase-13?)
- 13-13 — Phase 13 exit scenario integration test. Real Android device, the full exit-scenario walkthrough from §5. Bug fix sweep. (Cross-ref 2026-05-22: D-021 mandates pure-micro AND pure-evening usage patterns both work — currently the §5 walkthrough implicitly assumes evening-session; QA should verify both. D-027 §2 cold-open beats need either to be present in 13-13’s walkthrough OR explicitly marked as deferred to a post-Phase-13 onboarding sub-phase. §5 step 4 (“Complete onboarding tutorial”) may need editorial pass per D-027.)
If more sub-phases emerge from re-planning (likely — onboarding polish, error handling, edge cases on Health Connect provenance, mock-auth UX, push notifications) they append here as N+1, N+2, etc.
7. Per-area sub-phase mapping
Cross-reference so no area is starved. As of plan v1:
- Combat: 13-7, 13-8, 13-9.
- Quests: 13-5, 13-7 (quest-trigger), 13-9 (outcome→quest), 13-10.
- Character progression: 13-2 (D-016 spec), 13-3 (walker creation + class), 13-4 (streak + step→energy), 13-5 (tree allocation), 13-10 (keystone-unlock).
- Cross-cutting infrastructure: 13-1 (Android repo), 13-6 (faction), 13-11 (a11y/i18n), 13-12 (offline queue), 13-13 (exit test).
If after a few sub-phases land we notice one area is racing ahead and another is starved, re-balance at the next /work re-planning.
8. Dispatch posture
How orchestrator dispatches a sub-phase:
- CEO types
/work phase-13-N. - Orchestrator reads this plan, locates sub-phase N, confirms its prerequisite is met.
- Orchestrator dispatches the paired leads listed in the sub-phase (typically
tech-architect+mobile-developer; sometimes alsomechanics-designerornarrative-designerconsulted). - Each lead returns a structured report.
- Orchestrator commits the work in logical chunks per auto-commit policy.
- Orchestrator updates the roadmap row + this plan (mark sub-phase done, append commit SHA, expand the next skeletal placeholder if its shape has clarified).
- Orchestrator returns control to CEO with a planning prompt: “13-N landed. Proposed next: 13-(N+1) per plan. Alternative:
. Pick one or re-plan.”
Lore parallelism: at any point during Phase 13, CEO can dispatch narrative-designer for an independent lore increment (Quest 003, new NPCs, region deepening). Lore work does not consume Phase 13 dispatch budget; it runs alongside.
Re-planning cadence: Every sub-phase boundary. Plan v1 (this document) commits with the first sub-phase. Plan v2 commits with sub-phase 13-2 (after D-016 ratifies, point-award math becomes concrete, downstream sub-phases can be detail-planned).
Dispatch frequency: Estimate 1-2 sub-phases per CEO session. Phase 13 total runs ~13-20 sub-phases; estimate 6-10 CEO sessions to complete. No calendar deadline — exit gate is the §5 exit-scenario green run.
9. Risks + mitigations
Risk: Progression system spec drift. D-016 ratifies one shape; downstream sub-phases drift from it as they implement. Mitigation: every sub-phase that touches XP/level/points includes a checklist line “compared values against D-016 §system-reviewer cross-checks at sub-phase ship time.
Risk: Android-iOS contract divergence (forward-looking to Phase 15). Phase 13 ships Android-only; iOS in Phase 15 must inherit the validated contract. Mitigation: any platform-coupled decision in Phase 13 sub-phases is documented in the relevant ADR with explicit “iOS port inherits this” annotations. Specifically: mock-auth flow, Health Connect provenance contract, attestation token shape, offline queue semantics.
Risk: Backend endpoint surface bloat. Endpoint-per-feature adds up; the 8-endpoint baseline could grow to 20+ across Phase 13. Mitigation: tech-architect consolidates endpoints where possible (e.g. /walker/profile returns progression + streak rather than spinning up /walker/progression + /walker/streak as siblings unless real reason); Swagger doc kept current per sub-phase.
Risk: Lore-canon drift unnoticed because parallel. Lore work shipping in parallel could ratify things that conflict with Phase 13 assumptions (e.g. a new region introducing a faction-allegiance constraint that breaks the class-pick flow). Mitigation: game-director reviews any D-level lore ratification against the active Phase 13 sub-phase before it lands; system-reviewer cross-checks every D-level vs. open canon.
Risk: Mock-auth (ADR-0006) being baked in too deep, hard to swap to Firebase Auth (production target). Mitigation: auth integration on Android lives behind an interface; switching to Firebase Auth in the production-migration phase is a single adapter swap. Documented in 13-1 sub-phase ADR.
Risk: Combat encounter API drift from simulator. The simulator (data/src/sim/combat.ts) is the canonical math. If the backend encounter endpoint re-implements the loop separately, drift is inevitable. Mitigation: the backend MUST import the simulator from the data/ package and replay it server-side — the encounter endpoint is a thin wrapper over the simulator + persistence, not a re-implementation. Locked in 13-7’s ADR.
Risk: D-016 stalls. If progression-system /research takes more than 3 rounds without converging, Phase 13 sub-phases 13-3 onward (anything progression-touching) are blocked. Mitigation: if 3 rounds without convergence, CEO escalates to direct decision (no more rounds) — the system needs to ship even if the math is not perfect, and D-016 can be amended in a later D-level decision.
Risk: Phase 13 scope creep. Every sub-phase adds new “while we’re here” features. Mitigation: this plan is the contract; new ideas go into “13-N+1 skeletal” placeholders, not into the active sub-phase. Re-plan at boundaries, not mid-sub-phase.
10. Forward-references — composition with D-018..D-027
This section was appended on 2026-05-22 as an editorial re-check pass — no new D-canon, no sub-phase scope change. It documents how the ten D-decisions ratified 2026-05-21 → 2026-05-22 compose with Phase 13’s already-landed surface area, and which sub-phases (current or remaining) carry their forward-references.
The plan body (§1-§9) is the contract; this section is the cross-reference map. If a future re-check finds the body and this section in tension, the body wins and this section is corrected.
10.1 D-018 — Energy economy (action fuel + tight budget)
Status: Phase 13 combat encounter resolution already debits Energy per the D-018 ~30%-of-daily envelope; the sink shape was implicit in 13-7’s simulateEncounter integration and is now canonical. Sub-phases 13-7 (backend combat module) and 13-8 (Android Combat UI) operate inside the D-018 envelope without amendment. No code change required. Forward-references at 13-12 (offline queue must respect sink-debit ordering on sync; see D-018 §What-not-decide) and at any post-13 craft-attempt sub-phase (D-018 ~20%-per-attempt sink, currently un-surfaced because Phase 13 ships crafting tab as stub per §5 Mobile).
Canon link: D-018.
10.2 D-019 — Class system (5 factional classes + starting-cluster differentiation)
Status: Phase 13-3 shipped class.cartographer (Cech-aligned, Plenny start, cluster.first-steps) as the single playable class for the closed-beta cohort. As of 2026-05-22, the four remaining classes (class.pieczetarz / class.pielgrzym / class.komiwojazer / class.tropiciel) and their starting clusters (cluster.first-seal / first-lantern / first-route / first-sign, 8 nodes + 1 keystone each = 32 nodes + 4 keystones total) are authored at the data layer (commits c6c722e, 06d75b5, 83b5451) but NOT yet surfaced on the Android client. The §5 Data-layer feature-checklist item “At least 1 class instance authored” is satisfied; the implicit “ship 1, defer rest” posture documented in §4.2 is superseded by D-019 (canonical 5-class roster locked).
Phase 13 scope position: Phase 13 still ships 1 playable class (Cartographer) for the closed-beta exit scenario. Surfacing the other 4 in onboarding is a forward-reference to D-027 (see §10.10). Backend adapter mirror for the 4 new classes in backend/src/common/game-content.ts is intentional Phase 13 scope — tracked at ops/escalations.md Q8 FYI (2026-05-22). Mobile bundle currently bundles only Cartographer (per 13-3 BUNDLED_CLASSES); D-019 §3’s starting-cluster differentiation surfaces in mobile only after the class-selection endpoint lands (post-13 or in 13-12 if onboarding work expands per D-027).
Plan amendment: §3.3 “Character progression” originally enumerated “At least 1 class instance authored” as the Phase 13 contract. Update reading: §3.3 stands, but §4.2 “Class instance scope for Phase 13” should be read as CLOSED by D-019 — the canonical N=5 roster is now ratified, the W-level pick has been made (1 ships in Phase 13, 4 land at data layer per D-019 §2’s W-level follow-up which has now executed). No code regression; the §4.2 framing is historical.
Canon link: D-019.
10.3 D-020 — Combat encounter system (pull-based trigger + tiered risk-choice pool)
Status: Phase 13-7’s combat encounter API (ADR-0008 POST /combat/encounter family) implements encounter resolution but NOT the pool / trigger / tropy queue D-020 ratifies. Sub-phase 13-7’s POST /combat/encounter initiates from a quest beat directly (the only trigger source live today); D-020 §2 names two pool sources (step-driven + quest-beat-driven) of which only quest-beat-driven currently exists. The step-driven tropy accumulation, the badge taxonomy (easy / normal / hard / keystone-ready), and the visible-before-commit risk choice are all forward-references — they sit at post-13 W-level under mechanics-designer (B-level cadence tunables) + backend-engineer (pool persistence + visibility endpoint) + ui-designer (map-pin badge styling per D-022 §1).
Plan amendment: §3.1 “Combat” Phase 13 contract stands — Phase 13 ships encounter resolution, NOT pool building. Sub-phase 13-12 / 13-13 remain “offline queue hardening” and “exit-scenario integration test” per §6 skeletal entries; the D-020 pool trigger is NOT folded into Phase 13 unless CEO explicitly amends. If it is folded in, it belongs as a new sub-phase 13-N+1 (estimated ~1 dispatch session), not a 13-12 / 13-13 expansion. Recommended: defer to post-Phase-13.
Carve-out: D-020 §5 introduces trop / tropy terminology disambiguation (gameplay entity vs D-013 process slot). Glossary entry per D-017 is W-level narrative-designer follow-up; no Phase 13 schema change required — the encounter persistence layer (combat_encounters table, 13-7) is trop-agnostic on the wire.
Canon link: D-020.
10.4 D-021 — Daily loop (hybrid micro check-ins + evening session)
Status: D-021 ratifies the cadence the app is designed AROUND (3-5 micros + 1 evening session); it does NOT mandate any UI or notification surface in Phase 13. Phase 13’s current home + post-walk-sync + combat surfaces compose cleanly with both micro and evening usage (verified in §5 exit-scenario walkthrough). No code change required. Forward-references at 13-13 exit-scenario integration test (the walkthrough implicitly assumes a single evening-session pattern; D-021 §2 mandates pure-micro and pure-evening both work — flag for QA at 13-13).
Canon link: D-021.
10.5 D-022 — Map as live gameplay surface (diegetic centrality, navigational preservation)
Status: D-022 ratifies the 5-tab bar (Home / Tree / Factions / Quests / Craft) is preserved (D-014 §1 unchanged), and that Map is a diegetic gameplay artefact fronted by the Home tab, NOT a 6th tab. Phase 13’s 5-tab nav (per §5 Mobile feature-checklist + 13-4 Home implementation) is canon-aligned. The “Home fronts a Map widget that IS the encounter-queue UI” reading of D-022 §1 is a forward-reference — Phase 13’s Home currently renders region card + streak ribbon + quest pill + faction strip (per 13-4), not the live-rewriting Map widget. The Map widget per D-022 §1 + D-013 przepisać real-time curvature rewriting is a post-Phase-13 ui-designer + mobile-developer + tech-architect sub-phase (estimated 1-2 dispatch sessions, depends on D-020 pool surface). No Phase 13 regression.
Forward-reference also touches: D-022 §What-not-decide explicitly defers accessibility-mode rendering (e.g. high-contrast Map, screen-reader-readable Map state) — overlapping with D-029 candidate (currently in /research). See §10.11 below.
Canon link: D-022.
10.6 D-023 — Endgame (Atlas of rejestry — procedural editorial-commit instances)
Status: D-023 names the endgame surface (Atlas unlock at ~144 pts spent, procedural rejestr instances). Phase 13’s exit scenario (§5) ends at “first allocation on cluster.first-steps” — many tens of points BEFORE the Atlas unlock threshold. No Phase 13 surface area touched. D-023 is purely forward — earliest implementable phase is post-Phase-14 once the closed-beta cohort has had time to approach ~50 pts. Cross-reference noted for completeness; no code change required in Phase 13.
Canon link: D-023.
10.7 D-024 — Quest structure (6 region-linear sagas, 15 main + 3 hidden per region)
Status: D-024 ratifies the 6 × 18 = 108 quest distribution (90 main + 18 hidden) with strict linear chain within a region + off-spine hidden quests + Plenny-canonical-first cross-region order. Phase 13 has shipped Plenny quests 001-006 (per Lore parallel SHAs in “Current phase” / “Recent landings”); the chain Q001 → Q002 → … → Q006 already matches D-024 §2’s “strict linear chain” pattern. Sub-phase 13-5’s GET /quest/available + QuestGateEvaluator + KEYSTONE_GATE are the canonical implementation surface for D-024 §2’s hidden-quest gating. Quest 005 (niemilknacy-kurier, shipped in 13-10) is the first hidden quest with keystoneRequirement — fully D-024-compliant.
Phase 13 forward-reference: Plenny is 6 quests deep; D-024 mandates 15 main + 3 hidden = 18 per region. The remaining 12 Plenny main quests + 3 hidden Plenny quests are post-Phase-13 narrative-designer work. No Phase 13 regression — Phase 13 ships the vertical slice, not a full saga.
Canon link: D-024.
10.8 D-025 — Multiplayer scope (M1 package)
Status: D-025 ratifies async lightweight co-op + full guild infrastructure + scheduled regional events as Phase 13/14 scope, deferring real-time sync walking to post-Phase-16. Phase 13’s current backend + Android surface area has zero multiplayer code — no guild entity, no co-op session model, no event scheduler. Per D-025 §3 phasing, Phase 13 ships guild persistence + polling chat + lightweight co-op session reconciliation as the largest Phase 13 increment (~3-4 weeks W-level under tech-architect per D-025 §3). This is NOT in §6’s skeletal sub-phase list — D-025 is a Phase 13 scope expansion that needs CEO triage at the next planning boundary.
Plan amendment proposal (CEO triage): Add three new skeletal sub-phases to §6 covering (a) guild entity + chat polling, (b) lightweight co-op session model, (c) regional event scheduler + leaderboard. Sequence + detail TBD at next planning round. FLAG_LEAD: D-025 expands Phase 13 scope materially beyond §1’s “vertical slice” framing — the exit-scenario walkthrough (§5) does NOT cover any multiplayer path. CEO should decide whether Phase 13’s “closed-beta cohort needs” includes multiplayer or defers to Phase 14 VPS.
Canon link: D-025.
10.9 D-026 — Notifications (meaningful-state firing + Pratchett-warm Cech editorial voice)
Status: D-026 ratifies a 6-class notification firing matrix + 8 forbidden fire classes + voice register canon. Phase 13’s current Android client has zero push notification infrastructure — neither FCM token registration, nor per-class opt-in surface, nor the editorial-voice copy bank. D-026 §5 establishes 6 channel groups; per-class opt-in surface is a forward-reference to D-027 onboarding (§10.10) + a post-Phase-13 ui-designer + mobile-developer + narrative-designer sub-phase.
Phase 13 forward-reference: Phase 13 may ship a minimal D-026 surface as part of 13-12 (offline queue hardening) — specifically the FCM token registration + per-class opt-in toggles per D-027 §2 step 6. The full firing matrix (6 classes × ~324 hook lines across 108 quests per D-024) is post-Phase-13 narrative-designer work. No Phase 13 regression.
Canon link: D-026.
10.10 D-027 — Onboarding (diegetic Bertranda walkthrough as Quest 001 beat 1)
Status: D-027 ratifies that onboarding IS Quest 001 beat 1 — no meta-tutorial, no skippable overlay. The Phase 13-3 onboarding flow (splash → class pick → home) is partially D-027-aligned but predates D-027 canon and needs reconciliation. Specifically:
- Step 0-2 (splash + sign-in + permissions): mostly intact — Phase 13-1 mock auth + Phase 13-4 Health Connect permission prompt cover this.
- Step 3-5 (Bertranda hands Map + motto + 50-step register the hand): NOT IMPLEMENTED in Phase 13 — current onboarding goes splash → class pick → home directly. The diegetic Bertranda walkthrough + 50-step bar + Map widget first-impression are forward-references.
- Step 6 (notification opt-in): NOT IMPLEMENTED — see §10.9 above.
- Step 7 (class selection): Phase 13-3 ships class-pick screen, BUT currently as a UI screen BEFORE Quest 001 beat 1, not AS the closing surface of Quest 001 beat 1 per D-027 §3.
- Step 8 (Quest 001 beat 1 closes): Quest 001 exists data-layer; the beat-1-as-onboarding wrapper is not built.
Phase 13 forward-reference: Sub-phase 13-12 “Offline queue hardening” was originally scoped narrowly (per §6 skeletal entry). D-027 raises the question whether 13-12 OR a new sub-phase 13-12.5 / 13-N+1 absorbs onboarding reconciliation — Bertranda walkthrough expansion + 50-step register surface + class-selection-as-beat-1-close per D-027 §2-§3. Alternatively, the existing 13-3 class-pick UI is treated as adequate for closed-beta and the diegetic expansion lands post-Phase-13 (narrative-designer + ui-designer + mobile-developer paired). FLAG_LEAD: CEO triage required — Phase 13 plan §4.2 + §3.3 originally framed class-pick as a standalone onboarding step; D-027 reframes it as a within-Quest-001 closure. Either (a) ratify expansion into 13-12 or 13-N+1, or (b) accept the current 13-3 class-pick as Phase-13-final and schedule diegetic expansion post-Phase-13. Recommended: option (b) — preserve Phase 13 exit-scenario stability, schedule onboarding diegetic expansion as a Phase-13-followup or early Phase 14 task.
Sub-phase 13-13 (exit-scenario integration test) note: the exit-scenario walkthrough in §5 step 4 (“Complete onboarding tutorial”) needs an editorial pass to align with D-027 — either expanded to cover the §2 cold-open beats, or explicitly marked as “minimal-onboarding for Phase 13 closed-beta, full D-027 onboarding lands in 13-N+1 or post-13.”
Canon link: D-027.
10.11 D-029 candidate (accessibility, IN /research)
Status: D-029 is a candidate in ops/research/d-029-accessibility.md (per Q3 of the 2026-05-22 night plan) and is NOT canon. The candidate carries a HARD CLAUDE.md Pillar 1 amendment (broadening “step ingest” to “movement attestation” covering wheelchair propulsion / treadmill / stationary cycle / passive modes). Phase 13 has zero wheelchair / treadmill / stationary attestation code — all current ingest is HealthKit / Health Connect step counts. Forward-reference only: if D-029 ratifies, Phase 14 (VPS) or Phase 15 (iOS) adds the broader movement-attestation contract; D-022 §What-not-decide pre-deferred Map accessibility rendering to the same window. Out of scope for Phase 13.
Canon link: TBA — D-029 not yet ratified. Research artifact at ops/research/d-029-accessibility.md (pending).
10.12 Summary — what changes in Phase 13 as a result of D-018..D-027
Zero code-layer regressions identified. All ten D-decisions compose with Phase 13’s already-landed surface area without contradicting any sub-phase 13-1..13-11 deliverable.
Two FLAG_LEAD items for CEO triage:
- D-025 multiplayer scope (§10.8): Phase 13 originally framed as “vertical slice” without multiplayer. D-025 ratifies guild + co-op + events as Phase 13/14 scope. CEO must decide whether Phase 13 absorbs the M1 package (adding 2-3 new sub-phases) or defers all multiplayer to Phase 14 VPS.
- D-027 onboarding shape (§10.10): Phase 13-3 ships class-pick as a standalone UI step; D-027 reframes class-pick as the closing surface of an expanded Quest 001 beat 1 (Bertranda walkthrough + 50-step register + Map first-impression). CEO must decide whether Phase 13 absorbs the diegetic onboarding expansion (new sub-phase 13-12.5 / 13-N+1) or accepts current 13-3 as Phase-13-final.
Two minor amendments folded into the plan body:
- §4.2 “Class instance scope for Phase 13” reads as CLOSED by D-019 (5-class canonical roster ratified; 4 additional classes authored at data layer 2026-05-22 per
c6c722e/06d75b5/83b5451). - §3.1 “Combat” Phase 13 contract stands; the D-020 pull-based pool + badge taxonomy + visible-before-commit risk choice are post-Phase-13 forward-references (§10.3).
Plan version: v2 (2026-05-22 — §10 forward-references appended; no body changes).
Authored by: game-director per D-015 follow-up; §10 appended per night session 2026-05-22 Q10 (re-check pass against D-018..D-027).
Updated at every sub-phase boundary.