Phase 3 launch sprint. 13 tickets across server, client, copy. Atlas generation pipeline (terrain_reference, generate_atlas.py, Gemma naming), brand layer DB schema, Atlas implant panel (3 levels + heightmap viewer + overlays), hand-authored templates for Lendel + 4 core systems, brand corp TOML, brand_templates.toml (120-130 archetypes), wiki glossary, world seed wiring. Co-Authored-By: Claude Sonnet 4.6 (1M context) <noreply@anthropic.com>
117 lines
7.9 KiB
Markdown
117 lines
7.9 KiB
Markdown
# Sprint 35: Atlas — Server Tasks
|
|
|
|
**Goal:** Launch Phase 3 — build the atlas generation pipeline (terrain population, city placement, Gemma naming) and lay the brand layer DB schema, so all inhabited bodies have generated markers and the economics simulation uses world-seeded randomness.
|
|
|
|
**Branch:** `sprint-35/server`
|
|
**Agents:** Dudley (simulation/tooling), Tyre (architecture)
|
|
|
|
## New Tickets
|
|
|
|
| # | Title | Blocked by |
|
|
|---|-------|------------|
|
|
| #826 | Thread world seed from StartupMessage into economy simulation | — |
|
|
| #827 | Add brand_products, brand_inputs, system_fiscal schema and Phase 2 demand stubs | — |
|
|
| #839 | Batch populate terrain_reference column in systems.db bodies table | — |
|
|
| #832 | Build generate_atlas.py — terrain-aware sequential city placement and infrastructure generation | #839 |
|
|
| #833 | Gemma 2 batch naming pipeline for atlas geographic features | #832 |
|
|
|
|
## Key Decisions
|
|
|
|
- `decisions/architecture.md` — D-188 (biome_summary → planet_class rename, affects pipeline scripts), D-191 (Atlas Phase 3 scope — full pipeline spec: city placement algorithm, infrastructure gen, naming, markers.json schema)
|
|
- `decisions/economics.md` — D-189 (brand layer architecture — DB schema per section 5), D-190 (brand volume calibration — population-relative scale), D-185 (brands are not commodities — brand corps are commodity demand nodes), D-175 (corp taxonomy — Tier 1 brand corps), D-182 (TOML source of truth — make economy-db extends to brand tables)
|
|
|
|
## Notes
|
|
|
|
### #826 — Thread world seed into economy simulation
|
|
|
|
Small, self-contained. `server/src/simulation/mod.rs` initializes `EconSimResource` with `try_load_economy(0)` — the `0` is a hardcoded seed. Wire in the `world_seed` from `StartupMessage` (received during the IPC handshake). The seed is already available in the simulation startup path; find where `StartupMessage` is handled and thread the value through to `try_load_economy()`. Start here — it unblocks nothing else but is low-risk and closes the Sprint 34 loose end.
|
|
|
|
### #827 — Brand layer DB schema and Phase 2 demand stubs
|
|
|
|
Per D-189 section 5, add five new tables to `db/schema.sql` (or `server/data/systems-schema.sql` if that is the brand-layer schema file — check which file `make economy-db` reads):
|
|
|
|
- `brand_products` — full column list in D-189 section 5
|
|
- `brand_inputs` — `brand_product_id`, `commodity_id`, `quantity`
|
|
- `system_fiscal` — `system_id`, `corp_tax_rate`, `collection_efficiency`
|
|
- `corp_financial_state` — passive tracking (Phase 2: health metric only)
|
|
- `corp_lifecycle_events` — Phase 3 lifecycle state machine (Phase 2: stub table with correct schema)
|
|
|
|
Add composite index on `brand_products(corp_id, brand_category)` for UI queries (D-189 section 5).
|
|
|
|
Also author `wiki/economics/corporations/brands.toml` (new file) with TOML records for the 4 canonical brand corps: Calloway Distillery, Vins de Grand Vide, thrds, Bífröst Marmor. Each record registers those corps as commodity demand stubs at their home market nodes — they consume generic commodity inputs (per D-185: brands consume commodities, not the reverse). The copy team (#830) is authoring these same entries to `tier1.toml`; coordinate — the brand corps should appear in `tier1.toml` (copy) AND have separate `brand_products` entries (this ticket). Do not duplicate data; confirm the split before writing.
|
|
|
|
Extend `make economy-db` to compile brand tables alongside the existing pipeline. Add validation rules V-B01 through V-B05 (defined in the ticket description).
|
|
|
|
### #839 — Batch populate terrain_reference
|
|
|
|
The `bodies` table in `server/data/systems.db` has a `terrain_reference` column that is NULL for all 273 inhabited bodies. Write a batch script (Python fits alongside the existing `tooling/planet-gen/` scripts) that:
|
|
|
|
1. Queries all body rows with NULL `terrain_reference`
|
|
2. Constructs the expected wiki heightmap path: `wiki/star-systems/{system_slug}/bodies/{body_id}/heightmap.png`
|
|
3. Verifies the file exists
|
|
4. Updates the column
|
|
|
|
Log any bodies where the heightmap is missing so they can be flagged. This is the prerequisite for `#832` — `generate_atlas.py` reads `terrain_reference` to find the heightmap. Keep the script simple; it's a data population pass, not logic.
|
|
|
|
### #832 — Build generate_atlas.py
|
|
|
|
New Python pipeline at `tooling/planet-gen/generate_atlas.py`. Reuses `planet_simulation.simulate()` for terrain data. Per D-191 section 3 and 9:
|
|
|
|
**Pipeline order:**
|
|
1. Load heightmap via `terrain_reference` (populated by #839)
|
|
2. Analyze terrain: continent detection (flood-fill), habitability scoring (temperature + moisture + slope), river mouth identification
|
|
3. Place cities sequentially:
|
|
- Capital first: ~50% at river mouths, scored by habitability + coastal access + flat hinterland
|
|
- Rail corridor growth: cities 2-N follow the capital's terrain corridor
|
|
- New continent ports at cities 3-4 (cross-continent expansion)
|
|
4. Generate infrastructure: A* pathfinding for roads and rail on terrain cost grid, MST network connecting cities
|
|
5. Apply quadrant distribution constraint (cities should not all cluster in one area)
|
|
6. Apply ±25% noise for variation
|
|
7. Compute city count from population: `floor(log10(pop / 1_000_000))`, modified by `settlement_pattern` from systems.db
|
|
8. Write `markers.json` per body (schema per D-191 section 8: cities with lat/lon/population_tier/primary_function/gate_terminal/continent_id, roads, railroads, POIs)
|
|
|
|
**make target:** `make atlas-generate` — incremental, skips bodies where `markers.json` already populated. Deterministic per seed.
|
|
|
|
Naming step is NOT in this ticket — city names will be blank strings in this pass; `#833` fills them. Gate terminal POI: place at largest population center, occasionally scatter to a smaller one (per D-191).
|
|
|
|
Existing files to reuse: `tooling/planet-gen/planet_simulation.py`, `tooling/planet-gen/biome_config.py`. The `generate.py` script already calls `_build_markers()` for rivers/oceans/mountains — extend that structure rather than replacing it.
|
|
|
|
### #833 — Gemma 2 batch naming pipeline
|
|
|
|
Extend `generate_atlas.py` with `tooling/planet-gen/gemma_naming.py` — a batch client for the `sr-voice` binary. Per D-191 and D-191 cross-reference to D-138 (Gemma 2 voice pipeline):
|
|
|
|
For each body, send corridor-appropriate naming prompts:
|
|
- Prompt context: `planet_class`, `cultural_corridor`, `settlement_pattern`, `atmospheric_tone` + corridor palette
|
|
- Name: rivers, oceans, mountain ranges, regions, city names (already placed by #832, just unnamed)
|
|
- Naming patterns per D-189: `north_reach` → British/Australian inflection, `east_reach` → Korean/Japanese, `west_reach` → German/Dutch/Nordic, `south_reach` → Portuguese/Swahili, `inner_corridor` → pan-corridor neutral, `frontier` → founder surname + noun
|
|
|
|
Post-processing:
|
|
- Earth-name blocklist (filter obvious Earth names that slip through)
|
|
- Dedup check against full name corpus per body
|
|
- Estimated runtime: ~80 min for all 2,394 bodies — make this batch incremental
|
|
|
|
This ticket serves dual purpose: Phase 3 content delivery AND a quality test of the Gemma 2 naming pipeline ahead of its broader use.
|
|
|
|
The `sr-voice` binary lives in `server/src/voice/` — check existing voice pipeline callers in the codebase for the batch invocation pattern before writing new code.
|
|
|
|
## Dependency Chain
|
|
|
|
```
|
|
#826 (seed wiring) — standalone, start first (small)
|
|
|
|
#827 (brand schema + demand stubs) — standalone, parallel track
|
|
|
|
#839 (terrain_reference populate) → #832 (generate_atlas.py) → #833 (Gemma naming)
|
|
```
|
|
|
|
`#839 → #832 → #833` are sequential. `#826` and `#827` are fully parallel to the atlas chain. Atlas pipeline is the sprint's critical path.
|
|
|
|
## PR Workflow
|
|
|
|
```bash
|
|
tea pr create --repo jpmschweitzer/settled-reach --login schweitz \
|
|
--title "feat(simulation): atlas generation pipeline and brand schema" \
|
|
--description "Sprint 35 server work: terrain_reference population, generate_atlas.py, Gemma naming, brand DB schema, world seed wiring" \
|
|
--base main --head sprint-35/server
|
|
```
|