neon-sprawl-archived/docs/architecture/tech_stack.md

114 lines
6.3 KiB
Markdown
Raw Blame History

This file contains ambiguous Unicode characters!

This file contains ambiguous Unicode characters that may be confused with others in your current locale. If your use case is intentional and legitimate, you can safely ignore this warning. Use the Escape button to highlight these characters.

# Tech stack (baseline decision)
**Status:** Baseline for **prototype through early pre-production**. Revisit before vertical-slice freeze if tooling or hiring assumptions change.
**Constraints from product vision:** Solo operator, server-authoritative critical paths, fixed isometric 3D client, tab-target combat, data-driven skills/items/recipes/quests, optional PvP zones, eventual scale-out (not day one).
**Server runtime (locked):** **C# / .NET 10** — primary author has ~10 years C# experience; authoritative game logic, persistence, and ops stay in this stack.
**Client scripting (locked):** **GDScript** in Godot—fast iteration, native engine integration; server remains the only **C#** game-logic surface.
**Other operator skills:** **JavaScript** and **TypeScript** remain useful for content tooling and one-off scripts—**not** the authoritative server.
## Summary
| Layer | Choice | Role |
|--------|--------|------|
| Game client | **Godot 4.x** + **GDScript** | Rendering, input, camera, local prediction (if any), UI, telemetry emit |
| Game server | **C# / .NET 10** (ASP.NET Core) | Authoritative simulation, zones, combat/crafting resolution, persistence boundaries |
| RPC / messages | **Protobuf** (or **JSON** for earliest spike only) | Versioned contracts between client and server |
| Primary database | **PostgreSQL** | Characters, inventory, progression, economy ledger, idempotent transactions |
| Cache / presence (when needed) | **Redis** | Sessions, rate limits, hot read models—**defer** until second scaling pain |
| Content data | **JSON or YAML + JSON Schema** (or **CUE** later) | Skills, items, recipes, quests; validated in CI (can use Node or `dotnet` validators) |
| Repo / CI | **Git** + **GitHub Actions** or **Gitea Actions** | `dotnet build`, schema validation, optional Godot export |
## Client: Godot 4
The [`client/`](../../client/) Godot project targets **4.6** (`config/features` in `project.godot`). Older 4.x may work but 4.6 is the baseline for editor and manual testing.
**Why**
- Strong fit for solo iteration: fast reload, small install, no revenue cap.
- 3D isometric camera (orthographic or perspective), zoom, and **no rotation** are straightforward in a single-camera rig.
- **GDScript (locked)** for all client gameplay and UI code—quick reload, examples and addons match; share contracts with the server via **Protobuf** or **JSON** (spike), not shared C# assemblies.
- Networking: treat **WebSocket** or **TCP** as transport only; **authoritative logic stays on the ASP.NET Core server**, not in Godots high-level multiplayer templates, to avoid fighting engine assumptions.
**Prototype discipline**
- One contained district; no multi-region streaming in engine until pre-production handoff slice.
- Client sends intents (`MoveIntent`, `UseAbilityIntent`, …); server emits state deltas or snapshots.
**Plan B**
- **Unity** (6000 LTS track) if the art pipeline shifts; **server stays C#**—reuse patterns and types where practical.
**Defer**
- **Unreal** for this phase unless art direction *requires* it.
## Server: C# (.NET 10)
**Why**
- **ASP.NET Core** (minimal APIs or controllers) + **Kestrel**; WebSockets, gRPC, or raw TCP alongside HTTP health/metrics.
- **PostgreSQL** via **Npgsql**; **EF Core** (migrations) or **Dapper** + **FluentMigrator** / **DbUp**—pick ORM vs hand-written SQL and stay consistent.
- **Protobuf:** **Grpc.Net** or **protobuf-net**; JSON is acceptable for the first spike only.
- **Prototype shape:** single `GameHost` (or named) process—in-memory zone state + PostgreSQL for durable character/inventory; split processes only when metrics demand it.
**Pre-production**
- Optional read replicas or separate presence service; job queues only when needed.
## Server alternative (not default)
**TypeScript / Node** remains viable for tools-only or a secondary BFF; avoid splitting authoritative state across two runtimes unless there is a clear boundary (e.g. web shop vs simulation).
## Other server languages (optional later)
| If you… | Consider |
|---------|----------|
| Want a tiny deploy binary for a worker | **Go** — isolated sidecar, not replacing the main C# sim without a decision doc |
| Experiment | **Rust** — only for proven hot paths |
## Data and persistence
- **PostgreSQL** as source of truth for anything that must survive restarts or be audit-able (inventory, trades, progression).
- Migrations: **EF Core** or **FluentMigrator** / **DbUp** with **Npgsql**; keep migrations in-repo.
- **Avoid** client-trust for economy: craft outcomes, loot grants, and trades commit only after server validation + DB transaction where required.
## Content pipeline
- Author in **JSON/YAML**; validate with **JSON Schema** in CI (Node-based **ajv**/CLI, **dotnet**-based validators, or **CUE** later).
- Server loads tables at boot or hot-reloads in dev; client may receive **bundles** or hash-versioned blobs to avoid drift.
- Epic 3/7 decomposition modules (`RecipeDef`, `QuestDef`, …) map directly to these files.
## Observability
- **Serilog** and/or **OpenTelemetry** for .NET from early prototype.
- Align event names with `E9.M1 TelemetryEventSchema` in the vision doc; client batches to server or OTLP endpoint as capacity allows.
## Security (proportionate to phase)
- **Prototype:** TLS on public endpoints if exposed; auth token or session secret; minimal PII handling.
- **Pre-production:** Rate limits, input validation on all RPCs, admin tools behind separate auth.
## Explicit non-goals for stack selection
- Choosing a commercial “MMO middleware” that locks data formats or hosting.
- Client-authoritative combat or inventory.
- Full anti-cheat and bot defense before core loop fun is proven (track with E9.M4 workflows later).
## Revision triggers
Revisit this document if:
- Target platforms add **console** or **mobile** with hard certification constraints.
- Art pipeline commits to an engine not listed above.
- Co-op session model forces **P2P** or large physics sync (unlikely for tab-target isometric).
- Simulation CPU bottlenecks justify a **Go/Rust worker** for isolated workloads—document the split; **keep C# as orchestration** unless you rewrite the decision.
## Related docs
- [`neon_sprawl_vision.plan.md`](../neon_sprawl_vision.plan.md) — product locks and phase gates
- [`docs/decomposition/README.md`](../decomposition/README.md) — epic/module decomposition