Skip to content

Latest commit

 

History

History
283 lines (240 loc) · 23.6 KB

prd.md

File metadata and controls

283 lines (240 loc) · 23.6 KB

NIGHTCELL 7 — PRD traceability

Canonical requirements: NIGHTCELL 7: FALSE DAWN — PRD V1.3 (25 July 2026).

This file records the locked decisions and maps each PRD section to the code that implements it. When a decision changes, update this file in the same commit as the code (CLAUDE.md).

Not yet in the repo: the full narrative PRD text (story bible, mission scripts, art-direction prose, asset inventory). Commit it as docs/prd-v1.3.md so the document CLAUDE.md points at is actually here. This file is the engineering-facing extract and index, not a replacement.

Steam: readiness, requirements and the open payment-rule decision are in docs/prd-steam.md (assessment dated 2026-09-22, not a locked decision).


Locked V1 decisions (PRD §2)

Area Decision
Working title NIGHTCELL 7
Episode 1 FALSE DAWN
Genre First-person tactical action shooter, single-player + online multiplayer
Camera First person
Story structure Two playable opposing perspectives
First theater Fictional near-future Iran crisis
Free product Launcher, benchmark, training, dual-side demo, Multiplayer Alpha
Episode price $9.99 USD
Purchase includes Both sides, Complete Truth epilogue, all platforms
Subscription / microtransactions None
Multiplayer P0 V1 requirement, server-authoritative
V1 multiplayer mode 6v6 Team Deathmatch, private matches, optional bot fill
V1 multiplayer map Ardavan Yard (derived from Episode 1 architecture)
V1 throwable Frag grenade only — 2 per life, no resupply, no other gadget
Multiplayer access Free to verified accounts, no pay-to-win
Runtime target 60–90 minutes per campaign side
Engine / build Babylon.js / Vite
Physics Havok client-side; simplified authoritative server simulation
UI Preact for menus and HUD only
Marketing site Next.js App Router, custom art-directed design system
Repository One Git repository and pnpm workspace
Separate repositories Prohibited for V1
Deployment Railway for every deployable application service
Public domain nightcell7.com
API base https://nightcell7.com/api/v1
Realtime endpoint wss://nightcell7.com/api/v1/multiplayer/sync/...
Multiplayer framework Colyseus on Node.js
Ephemeral realtime state Railway Redis
Durable database Postgres + Drizzle
Authentication Better Auth, verified email
Payments CoinPayPortal only — direct Stripe integration prohibited
Email Resend
Asset/content storage Cloudflare R2
Mobile touch play Out of scope
DRM Low-friction entitlement, no invasive DRM

Current game art direction — IRON RAIN (2026-09-16)

The Ardavan runtime uses original modern military industrial scenery: pale concrete, slate-blue equipment, orange utility markings, dark asphalt and cool daylight. This replaces the earlier night/sodium presentation. All 27 scenery, vehicle, prop, world-weapon and operator models are rebuilt; the approved first-person C7 and its coating/normal maps remain unchanged. Two original animated operators, new environmental surfaces, lighting, effects, deployment menu and field HUD ship as one runtime set. Obsolete model and texture files are removed.

The episode title remains FALSE DAWN. The map collision layout, combat rules and budgets remain unchanged. Reproduction and verification are documented in tools/art/iron-rain/README.md; every website capture identifies its source commit in apps/site/public/media/yard/manifest.json.


Section index

PRD § Requirement Implementation
§5.2 $9.99 episode, one purchase covers both sides packages/entitlements/src/catalog.ts
§5.4 No pay-to-win in multiplayer packages/game-core/src/weapons.ts (multiplayer flag), multiplayer-sim loadout filter
§5.6 Refund revokes entitlement, free multiplayer unaffected packages/entitlements/src/entitlements.ts
§8 Six mission variants over three shared locations packages/game-core/src/campaign.ts
§8.1–8.2 Shared timeline and cross-campaign events campaign.ts (SHARED_TIMELINE)
§9 Free demo, either side first, no account required game-core/src/ids.ts (DEMO_MISSIONS), progress.ts (canStartMission)
§10.7 Complete Truth unlocks only after both sides progress.ts (shouldUnlockCompleteTruth)
§12.1 Movement set and feel packages/multiplayer-sim/src/movement.ts
§23.1 Free sandbox scenes need no account apps/game/src/modes.ts, access.ts (PLAY_MODE.SANDBOX)
§12.4 Health/armour, regen ceiling, no bullet sponges packages/game-core/src/damage.ts
§12.6 Difficulty changes tactics, not enemy health packages/game-core/src/difficulty.ts
§13.1 Five hero weapons, fictional (see §13.1 note) packages/game-core/src/weapons.ts
§13.2 One throwable: the frag grenade packages/game-core/src/grenades.ts, multiplayer-sim/src/grenades.ts
§13.3 Friendly-fire and identification rules multiplayer-sim/src/hitscan.ts (team filter), grenades.ts (resolveBlast)
§17.2 Single-repository mandate pnpm-workspace.yaml, CLAUDE.md
§17.3 Monorepo layout repository root
§17.5 Railway topology and public routing infra/railway/, services/gateway/src/routes.ts
§17.6 Health checks, structured logs, env validation, SIGTERM packages/observability/src/index.ts
§17.7 Local development mirrors production paths tools/release/dev.mjs
§18.1 Multiplayer Alpha scope packages/game-core/src/match-rules.ts
§18.2 Ardavan Yard, headless collision map, checksum multiplayer-sim/src/map.ts
§18.3 Authority model — what the server owns multiplayer-sim/src/simulation.ts
§18.4 Prediction, reconciliation, interpolation apps/game/src/net/prediction.ts
§18.5 Handshake and machine-readable rejections multiplayer-protocol/src/{version,codes}.ts
§18.6 Canonical endpoints, one-time tickets multiplayer-protocol/src/ticket.ts, services/api
§18.7 Gateway/API/multiplayer/worker/cron daemons services/*
§18.8 Sharding, regions, drain services/multiplayer/src/index.ts
§18.10 Reconnect grace, aborted matches not counted simulation.ts (expiredSeats), codes.ts (isRankableTermination)
§18.11 Bots use the same rules, labelled, never counted as players multiplayer-sim/src/bots.ts
§18.12 Moderation: reports, blocks, bounded quick chat services/api/src/app.ts, multiplayer-protocol/src/messages.ts
§19 Local save schema and migration packages/save-data/src/index.ts
§20 Marketing site product requirements apps/site/
§21 DIVIDED SIGNAL art direction apps/site/app/globals.css, packages/ui/src/index.ts
§22.5 Performance budgets, API never cached apps/game/vite.config.ts, gateway/API cache-control
§23 Access model, display names, guest claim, sessions packages/auth/src/index.ts
§24 CoinPayPortal only: checkout, states, webhooks, reconciliation packages/coinpay/, packages/entitlements/src/orders.ts, services/worker, services/cron
§25 Data model packages/database/src/schema.ts
§26 Entitlements and content delivery packages/entitlements/, packages/content-schema/
§27 PWA caching rules apps/game/vite.config.ts
§28 Electron security, purchase flow, cross-play apps/desktop/src/{main,preload}.ts
§29 Centralised API surface services/api/src/app.ts
§30.4 Tick rate, snapshot rate, rewind cap, budgets multiplayer-sim/src/constants.ts
§33.1 Gateway security headers, forwarding trust services/gateway/src/routes.ts
§33.3 Multiplayer integrity and anti-cheat posture simulation.ts, input.ts
§34 QA — unit, integration, load/soak *.test.ts, tools/multiplayer-loadtest/
§36 Scope priorities this file + README.md status

§13.1 note — a fifth weapon, 2026-09-22

§13.1 said four hero weapons, on the principle that "four excellent weapons have more value than twenty weak weapons". The M9 Hammerfall is a fifth, and the principle is intact.

That line is an argument against power creep and filler: a fifth assault rifle with slightly different numbers would be exactly what it warns about. The M9 is not that. Every other weapon in the game is hitscan, and this one puts a projectile in the air with a blast at the end of it. It adds a verb, not a variant, and it is the only weapon whose shots can be dodged, led, or taken cover from after they are fired.

It stays inside the locked rules:

  • Not pay-to-win. Bought with credits earned in play at 800, roughly eight kills. Credits are never purchasable with money (docs/prd.md, "Prohibited in V1"), so this adds nothing to the storefront.
  • Not power creep. One tube, a 3.4 s reload and five in reserve. A miss costs more than a miss with anything else in the yard, and the self-damage fraction is 0.75, so firing it at your own feet kills you.
  • Fictional, like the rest of the family. Original geometry, built by tools/art/iron-rain/generate.py (launcher() and rocket()).

If a sixth is ever proposed, it has to clear the same bar: a new verb, not a new stat line.

Cast and first-run onboarding, 2026-09-23

Cast. The supporting cast (Jonas Vale, Director Mara Vey, Colonel Arman Daryan, Silas Kade), the four factions and MIRAGE now live as data in packages/game-core/src/cast.ts, taken from the story bible (PRD §7.5 to §7.7). The site's /characters page and both dossiers render it, and so does the game's first-run briefing, so no surface can describe a person differently. It is public copy under the home-page timeline's rule: who these people are and what the player sees of them early, never what the campaigns reveal. Tests in cast.test.ts refuse the reveals (who authorised the cleanup, what Nightcell 7 designates), any Arabic-script text while Farsi awaits native review, and a Daryan written as a villain. Both protagonists get a circle of the same size (§14.3).

Onboarding. A first-time player gets a briefing on the deploy gate (their side's institution and whose story it is, from the same cast data) and then a coach in the yard that teaches one control at a time in §10.1's order and advances only when the player does the thing. Skippable from the gate (Esc); remembered in nc7.onboarded. Logic is pure in apps/game/src/onboarding.ts.

Budgets held in code

Changing any of these is a product decision, not a tuning tweak.

Budget Value Source of truth
Authoritative tick 30 Hz (33.3 ms) multiplayer-sim/src/constants.ts
Snapshot cadence ~20 Hz same
Accepted client input ≤60 Hz multiplayer-protocol/src/input.ts
Movement time per player per tick 1.25 × tick simulation.ts (DT_BUDGET_PER_TICK_MS)
Lag-compensation rewind cap 200 ms constants.ts (MAX_REWIND_MS)
Remote interpolation delay ~100 ms apps/game/src/net/prediction.ts
Reconnect seat hold 20 s game-core/src/match-rules.ts
p95 server simulation < 20 ms at certified capacity tools/multiplayer-loadtest
Ticket TTL 30–60 s, single use services/api/src/env.ts
Shell download ≤ 15 MB content-schema (DOWNLOAD_BUDGET_BYTES)
Demo route download ≤ 150 MB same
Paid episode ≤ 1.2 GB preferred, 1.5 GB hard gate same
Multiplayer incremental ≤ 250 MB same

Prohibited in V1

Encoded in CLAUDE.md and enforced by review:

  • A second payment processor, or any direct Stripe code, keys, webhooks or docs
  • Subscriptions, battle passes, loot boxes, paid weapons, paid matchmaking priority
  • Ranked play, skill rating, clans, tournaments, voice chat, free-form text chat
  • Spectator mode, replays, co-op campaign, player-hosted authoritative servers
  • Peer-to-peer or host-migrated multiplayer authority
  • Kernel-level anti-cheat
  • Native mobile play
  • Throwables beyond the frag grenade — the other five entries in GADGET are campaign fiction, not multiplayer content, and stay that way for V1
  • Separate repositories for the site, game, backend, multiplayer or infrastructure
  • Direct client connections to internal Railway service domains
  • Selling the second campaign or the true ending separately

Open gates before public launch

Gate Owner Status
Title and domain clearance (registrar checkout + lock) Product Not started
Trademark screening (USPTO/WIPO/EUIPO/UKIPO + common law) Legal Not started
CoinPayPortal production approval Product Not started
Digital tax classification and jurisdiction review Finance Not started
Iranian/Iranian-diaspora cultural consultant Product Not started
Native Farsi dialogue, subtitle and signage review Product Not started
Asset provenance and license audit Tech art Not started
Multiplayer network load certification on a deployed shard Engineering Simulation gate only
Railway production readiness checklist Engineering See infra/railway/README.md
Security review Engineering Not started
Visual QA against signed-off design Design Design not signed off

Tactical art integration — 2026-09-16

All 31 runtime models receive the full tactical art pass documented in docs/art/full-tactical-overhaul.md. Original C7 weapons replace the legacy weapon geometry. Licensed character rigs/animation and scenery base meshes remain licensed inputs; the provenance manifest distinguishes them from original work. Shared surface textures are regenerated and the three palette atlases are removed from runtime loading. The 9 MiB asset guard remains in force.

Four mirrored low-cover volumes at x ±10, z ±31 match the new concrete cover. They are part of the authoritative map, so content compatibility advances to 1.1.0 while the wire protocol remains 2. Both game and multiplayer service must ship this content revision together. Placement preserves the imported glTF coordinate transforms, including quarter-turn cover orientation and weapon muzzle direction. The website gallery is recaptured from the integrated game.

2026-09-16 — M2 graphics and public demo repair

M2 retires every legacy runtime model/texture filename and consolidates 31 former model entries into 28 original tactical GLBs. No licensed legacy meshes, rigs or animation clips remain in the active art build. The approved C7 rifle, field case and low cover stay in the unified inventory. Content revision advances to 1.2.0; wire protocol 2 and collision volumes stay unchanged. The public demo link always opens Team Deathmatch, combat pauses behind the menu, and a single simulation clock owns bot respawn. New character rigs, faction-safe roster construction, visibility-aware navigation and corrected aim restore visible opponents and return fire. Competitive server TDM limits remain unchanged. Details and full coverage are in docs/art/modern-assets-and-demo.md.

Additional free-play yards (2026-09-27)

The free-play deploy gate offers Ardavan Yard, Saffron Freight and Nacre Relay. Saffron Freight uses staggered amber freight stacks and connected outer flanks; Nacre Relay uses ivory relay houses surrounding an open cross-shaped plaza. Each has original architectural art generated from shared collision volumes. The chosen yard persists across mode, difficulty, operator and time-of-day changes, and is directly addressable with ?yard=saffron_freight or ?yard=nacre_relay. Bot combat, movement, projectiles and respawns use that same map. The competitive online map remains Ardavan Yard.

Yard environment expansion (2026-09-27)

All three yards include parked utility helicopters and patrol jeeps as static cover, and four walkable stair flights each. Saffron Freight mixes cargo loading roofs, a tank farm, convoy cover and an aircraft service bay. Nacre Relay mixes two relay rooftops with field shelters, a bunker and an aircraft plaza. Both use the existing environment asset kit, with the largest industrial structures as perimeter landmarks. Vehicle driving and flight controls are outside this change. Shared collision is authoritative for vehicles, aircraft tails, steps and decks.