diff --git a/modules/rust/PLAN.md b/modules/rust/PLAN.md index a8db9f2..bfc74eb 100644 --- a/modules/rust/PLAN.md +++ b/modules/rust/PLAN.md @@ -353,4 +353,95 @@ is invalidated at once, and **"gone, and that is fine" is a success**, not a fai - **`start.bat`'s RCON password is `letmein` in plaintext with `rcon.web 1`.** Acceptable on a loopback dev rig, and it must never be the shape anything published copies. +## 7. Contract coverage audit + +Added 2026-09-15 after re-reading the whole kit rather than only chapters 3–5. **The first draft of +§5 was built from the game-facing chapters and under-planned the website module by a wide margin.** +Every element of the contract is listed below with where it lands; the unplanned ones are the point +of the table. + +### The server handshake — ten registrations plus two hooks (ch. 2) + +| Call | Planned? | Where | +|---|---|---| +| `registerRoutes` | yes | 3 | +| `registerTeamProvider` | yes | 6 | +| `registerEventBudgets` / `OptionSources` / `Leases` / `Actions` | yes | 7–8 | +| `onBoot` / `onShutdown` | **implicit only** | make explicit in 1 | +| `registerExtension` | **no** | the dry run's own manifest declared `admin.users.detail` | +| `registerNotificationStreams` | **no** | — | +| `registerEventTriggers` | **no** | — | +| `registerAudiences` | **no** | — | +| `registerEngagementSeeds` | **no** | — | +| `registerAnnounceLeg` | **no** | — | +| `registerPostHook` | **no** | — | +| `registerSlashCommands` | **no** | — | + +**The template registers eight of these and the plan covered three.** Triggers, audiences and +engagement seeds are in `template/server/index.js` as a matched set — a trigger declares the payload +and its audience `ceiling`, an audience resolves people over module data, and seeds ship the bodies +and rules. None of the three was in §5. + +### The bundle's own parts + +| Part | Planned? | Note | +|---|---|---| +| `module.json` `id` / `coreApi` / `capabilities` | yes | 1, 3 | +| **`mounts` and prefix choice** | **no** | shares one namespace with core's, and the loader's probe cannot see core's root-mounted endpoints | +| `schema.sql` | yes | 2 | +| **`purge.sql`** | **no** | required whenever a schema ships | +| **`swagger-fragment.json` + generator + `check:swagger`** | **no** | fixed filename, merged verbatim, must be committed and checked current | +| **`vite.config.js` aliases / shims / `checkExternals`** | **no** | the kit calls this the highest-risk mechanical detail in the system | +| **`checkImports.js`** | **no** | the guard that makes a reach into core's tree fail the build | +| **`release.yml`, install manifest, `sha256`, host allowlist** | **no** | there was no packaging phase at all | + +### The client half + +| Part | Planned? | Note | +|---|---|---| +| `registry.registerRoutes` / `registerNav` | yes | 3 | +| **`declareModuleSlot`** | **no** | the kit: *"you will need it the moment your game has anything like a guild"* — so phase 6 | +| `registerFeatureProvider` | **no** | how a nav row becomes conditional | +| **UI kit discipline** | **no** | `PublicLayout` needs `shell`; `PageHeader` takes `eyebrow`/`title`/`lead`/`center` and drops unknown props silently | + +### Beyond the module + +| Item | Planned? | Note | +|---|---|---| +| Sidecar rpc correlation | implicit | needed by 7–8; state it in 1 | +| **Asset bridge (ch. 3 §2b)** | **no** | Rust's item icons and 2,590 skin ids are exactly the "content already on the game host" case | +| **`.profile` landing page** | **no** | three repos added is precisely when it is owed | +| **`runicgateway.com`** | **no** | a second game is a headline platform change | +| **Android app** | **no** | it feature-detects `capabilities` and must render a site whose module it has never heard of | +| `docs/` | yes | 11 | + +### What this does to the phase list + +The gaps are not evenly distributed: most land in the website module, which the original §5 treated +as three phases and which the kit treats as the bulk of the work. The phase list needs a packaging +phase, a notifications-and-engagement phase, and explicit bundle-mechanics work inside phase 1 — +plus decisions on the optional surfaces (slash commands, extension slots, the asset bridge) before +they can be scheduled. Those decisions are §8. + +## 8. Questions this plan cannot answer for itself + +Open, in rough order of how much they change the schedule. None is blocking phase 0. + +1. **Notifications and engagement** — does v1 ship triggers, audiences and engagement seeds, or is + that a later workstream? The template treats them as core furniture; skipping them means a Rust + site that cannot mail anybody about anything. +2. **Discord slash commands** — the platform has a bot and `registerSlashCommands` exists. Does the + Rust module claim any? +3. **Extension slots** — the dry run's manifest declared `admin.users.detail` (a user's Rust + identities inside core's admin user page). Keep it? +4. **The asset bridge** — item icons and skins over the bridge, or not in v1? It is a whole + protocol's worth of work and the site renders without it. +5. **Android** — does the app get Rust support in this workstream, or does it stay UO-only until the + module ships? +6. **Which mount prefixes**, given they share a namespace with core's own. +7. **Server scale** — how many Rust servers should the first release support in the UI? The dry run + says the module holds one client per server; the pages differ a lot between one and six. +8. **Wipe retention** — when a wipe truncates gameplay data, what survives? All-time rollups, or a + clean slate each month? + [kit]: https://gitea.whitlocktech.com/RunicGateway/Integration-kit