From 2c3e3ff5eb2eb49e3794e0e535414713c5fa2e3d Mon Sep 17 00:00:00 2001 From: Jeroen Schweitzer Date: Sun, 19 Apr 2026 15:51:17 +0200 Subject: [PATCH] =?UTF-8?q?fix(content):=20PR=20#133=20review=20=E2=80=94?= =?UTF-8?q?=209=20remaining=20items=20resolved?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Closes 9 of 10 review items (blocker 1 handled in add2507e + d78d3b59): - decisions/economics.md: reformat D-189 §5 amendment to standard Amendment (YYYY-MM-DD) block pattern (review #4) - tooling/planet-gen/sol_name_fixes.py: dedup guard + argparse --dry-run (reviews #5, #10a) - tooling/planet-gen/sol_markers/earth_features.json: trim to 11 cities with selection rationale (review #6A); user-approved rebalance Sydney → Lagos and London → Brussels (review #6B) - wiki/star-systems/GJ-380/bodies/GJ380c/markers.json: 2 secondary features renamed to Akan/Asante register — Kesset → Nkwanta Beck, Holt Spur → Bosomtwe Spur (review #7) - docs/atlas/hand-refine-log.md: Aethelred lore-migration documentation + see-also cross-link to refine_log_849.md (reviews #8, #13) - tooling/planet-gen/refine_log_849.md: rebalance addendum - wiki/star-systems/GJ-0/bodies/GJ0d/markers.json, server/data/ systems.db: re-synced after rebalance Stub depth (review blocker #2) handled via split — tracked as follow-up ticket #861 (three-layer narrative authoring). Final Earth cities (11): Beijing, Brussels, Cairo, Delhi, Istanbul, Lagos, Moscow, New York, São Paulo, Singapore, Tokyo. Co-Authored-By: Claude Opus 4.7 (1M context) --- decisions/economics.md | 3 +- docs/atlas/hand-refine-log.md | 21 ++++++ server/data/systems.db | Bin 5746688 -> 5746688 bytes tooling/planet-gen/refine_log_849.md | 19 ++++++ .../sol_markers/earth_features.json | 63 ++++-------------- tooling/planet-gen/sol_name_fixes.py | 46 +++++++++++-- .../GJ-0/bodies/GJ0d/markers.json | 28 ++++---- .../GJ-380/bodies/GJ380c/markers.json | 4 +- 8 files changed, 109 insertions(+), 75 deletions(-) diff --git a/decisions/economics.md b/decisions/economics.md index 8df4cbb5e..66efac675 100644 --- a/decisions/economics.md +++ b/decisions/economics.md @@ -337,7 +337,8 @@ This domain covers: currency system, commodity taxonomy, shadow economy, corpora **5. DB Schema** - `brand_products`: `brand_product_id`, `corp_id`, `product_name`, `brand_category` (8 values), `value_trajectory`, `scarcity_class` (`capped` / `constrained` / `scalable` / `unlimited`), `product_subcategory`, `base_premium_multiplier`, `premium_floor`, `origin_system`, `terroir_locked`, `currency_denomination`, `shadow_viable`, `brand_tier` (`halo` / `volume`), `halo_brand_id` (for volume tiers), `price_tier` (enum — see below) - - `price_tier` enum (5 values — amended Sprint 36 per team decision; closed enum locked on sprint-36/copy branch): `mass` (widely accessible, lowest price point; commodity_branded volume tiers) / `premium` (above-average quality signal; most volume tiers across categories) / `luxury` (aspirational, restricted availability; terroir and design_heritage halos) / `flagship` (pinnacle output, ultra-scarce; Veblen curve inflection; max 1 per brand, lore-grounded scarcity ceiling required) / `institutional` (B2B contract pricing, not market price; service_premium and platform_catalogue) + - `price_tier` enum (5 values): `mass` (widely accessible, lowest price point; commodity_branded volume tiers) / `premium` (above-average quality signal; most volume tiers across categories) / `luxury` (aspirational, restricted availability; terroir and design_heritage halos) / `flagship` (pinnacle output, ultra-scarce; Veblen curve inflection; max 1 per brand, lore-grounded scarcity ceiling required) / `institutional` (B2B contract pricing, not market price; service_premium and platform_catalogue) + - **Amendment (2026-04-19):** `price_tier` valid values were not defined in the original decision. Locked to the five values above per team decision, Sprint 36. - `brand_inputs`: `brand_product_id`, `commodity_id`, `quantity` - `system_fiscal`: `system_id`, `corp_tax_rate`, `collection_efficiency` (derived from `shadow_economy_intensity`) - `corp_financial_state` + `corp_lifecycle_events` tables for acquisition/startup lifecycle diff --git a/docs/atlas/hand-refine-log.md b/docs/atlas/hand-refine-log.md index 3f7b01cac..523b1e5c5 100644 --- a/docs/atlas/hand-refine-log.md +++ b/docs/atlas/hand-refine-log.md @@ -148,6 +148,27 @@ River and ocean collisions (Rio Grande ×23 rivers, Steinbruch ×19 rivers, Ridg - **"Jade Harbor" city on 20 bodies:** Widespread collision in generated content. The Gemma batch used this as a fallback east_reach city name. Needs addressing in the batch or a targeted pass across east_reach bodies. - **"Rio Grande" river on 23 bodies:** Portuguese fallback. Fix in the south_reach naming templates or targeted pass. +*See also: `tooling/planet-gen/refine_log_849.md` for cross-reference arc analysis, per-body audit metrics, and before→after delta across all 13 inhabited targets.* + --- *Next refine pass: re-run `atlas_quality_analysis.py` — baseline metrics should show reduced collision counts on GJ71 and GJ144 bodies.* + +--- + +## Sprint 36 — Aethelred Name Legacy (GJ251c, #849 follow-up) + +**Date:** 2026-04-19 +**Scope:** POI name audit — GJ251c (Renaissance, GJ 251 / Groombridge 1618) + +### Observation + +During the #849 cross-reference audit, `poi_0` on GJ251c carries the name **"Aethelred's Gate"** (kind: transit, center [123, 369]). + +The name is intentional. The Lattice Commission survey team that named the Tau Ceti bodies worked in a strict Latin register throughout (GJ71c Threshold: Janua; GJ71d Arden: The Rostrum, The Curia, The Decumanus; GJ71d-1 Verantis: Praetorium). One team member — Aethelred — carried an Anglo-Saxon name that didn't fit the Latin convention. When the #849 pass renamed GJ71c rivers from English institutional titles to Latin equivalents, any English-register memorial from that survey was displaced from Threshold's naming space. + +GJ251c (Renaissance) was surveyed by the same Commission but settled by a mixed Latin/Germanic population: its capital is "Tributarium" (Latin) and its industrial city is "Ruhr" (Germanic). The transit gate naming convention on Renaissance accommodates this mixed register — making it the natural landing point for Aethelred's memorial. Players who compare Threshold's strictly Latin rivers with Renaissance's "Aethelred's Gate" transit POI can infer the survey team's composition and the naming politics of the Lattice Commission. + +### No changes made + +`poi_0: "Aethelred's Gate"` on GJ251c — preserved as-is. No markers.json edits. No DB sync required. diff --git a/server/data/systems.db b/server/data/systems.db index 56ad83082f308ab522b23fd180714269b43e90dd..be71b3dd2d13b87397d4e69c4e9a16d4815cb32e 100644 GIT binary patch delta 5387 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 delta 5241 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 diff --git a/tooling/planet-gen/refine_log_849.md b/tooling/planet-gen/refine_log_849.md index 0ee8727ec..d16a99241 100644 --- a/tooling/planet-gen/refine_log_849.md +++ b/tooling/planet-gen/refine_log_849.md @@ -174,6 +174,19 @@ suffixes incompatible with the British-Isles naming style. **DB sync:** `generate_atlas.py --body GJ380c` ✓ +**Addendum (PR #133 review):** Initial pass left GJ380c 100% Anglo-British register with zero +cross-corridor influence from the Kumasi/south_reach trade lanes. Added two secondary features +in Akan/Asante register, keeping primary features (Aldren capital, Durneth Range, Rethain Sea) +in their established Anglo register: + +| Feature type | Old name | New name | Reason | +|---|---|---|---| +| river | The Kesset | Nkwanta Beck | Nkwanta = Akan "junction/crossroads" — trade-route name; Beck suffix localizes it | +| mountain | Holt Spur | Bosomtwe Spur | Bosomtwe = sacred Asante lake in Ghana; Spur suffix preserved from Groombridge convention | + +**Corridors are tendencies, not borders** — capital and primary geography stay Anglo-British; +peripheral features reflect Kumasi trade influence. DB re-synced. + --- ### GJ 699 — Barnard's Star system @@ -261,6 +274,12 @@ Ankara, Karachi, Shanghai, Mumbai, Jakarta, Dhaka, Manila, Bangkok, Seoul, Osaka Kolkata, Lahore, Shenzhen, Bangalore, Ho Chi Minh City, Luanda, Addis Ababa, Santiago, Taipei, Hong Kong, Casablanca. +**PR #133 review rebalance (user-approved Option 1 + London swap):** +- `Sydney → Lagos` — improves African representation (Cairo + Lagos = 2 African cities; Sydney was the weakest cultural-touchstone anchor). +- `London → Brussels` — Brussels chosen for future-strong-EU-capital setting fit over London's legacy cultural weight. + +**Final 11:** Beijing, Brussels, Cairo, Delhi, Istanbul, Lagos, Moscow, New York, São Paulo, Singapore, Tokyo. + **Generator note:** sol_import.py has no `--top-n` city filter — it uses the full earth_features.json list. If Sol is regenerated, earth_features.json should be trimmed to the 11 kept cities, or a filter added in sol_import.py. Filed as finding in #853. diff --git a/tooling/planet-gen/sol_markers/earth_features.json b/tooling/planet-gen/sol_markers/earth_features.json index c44cd41e2..7ad1cce15 100644 --- a/tooling/planet-gen/sol_markers/earth_features.json +++ b/tooling/planet-gen/sol_markers/earth_features.json @@ -1,5 +1,6 @@ { "GJ0d": { + "_city_selection_note": "11 cultural touchstones, one per major historical/cultural cluster. Criterion: would a player setting a bookmark to 'Earth' recognize this city? Full 46-city reference list is in git history (trimmed Sprint 36 #849). PR #133 review rebalance: Sydney → Lagos (African representation); London → Brussels (future EU capital fit). To adjust: edit this array and re-run sol_import.py, then generate_atlas.py --body GJ0d.", "oceans": [ {"name": "Pacific Ocean", "center": [128, 440]}, {"name": "Atlantic Ocean", "center": [128, 170]}, @@ -33,62 +34,22 @@ {"name": "Murray", "mouth": [170, 417]} ], "cities": [ - {"name": "London", "center": [79, 260], "population": 9000000, "region": "europe"}, - {"name": "Istanbul", "center": [83, 279], "population": 15000000, "region": "europe"}, - {"name": "Moscow", "center": [72, 294], "population": 12700000, "region": "europe"}, - {"name": "Paris", "center": [80, 261], "population": 11000000, "region": "europe"}, - {"name": "Berlin", "center": [77, 269], "population": 3700000, "region": "europe"}, + {"name": "Brussels", "center": [80, 266], "population": 2100000, "region": "europe"}, + {"name": "Istanbul", "center": [83, 279], "population": 15000000, "region": "europe"}, + {"name": "Moscow", "center": [72, 294], "population": 12700000, "region": "europe"}, - {"name": "Mexico City", "center": [107, 101], "population": 21800000, "region": "north_america"}, - {"name": "New York", "center": [87, 130], "population": 20100000, "region": "north_america"}, - {"name": "Los Angeles", "center": [93, 95], "population": 13200000, "region": "north_america"}, - {"name": "Toronto", "center": [84, 123], "population": 6200000, "region": "north_america"}, - {"name": "Chicago", "center": [85, 115], "population": 9500000, "region": "north_america"}, + {"name": "New York", "center": [87, 130], "population": 20100000, "region": "north_america"}, - {"name": "São Paulo", "center": [143, 164], "population": 22400000, "region": "south_america"}, - {"name": "Lima", "center": [133, 131], "population": 10700000, "region": "south_america"}, - {"name": "Bogotá", "center": [121, 135], "population": 11300000, "region": "south_america"}, - {"name": "Rio de Janeiro", "center": [142, 168], "population": 13500000, "region": "south_america"}, - {"name": "Buenos Aires", "center": [151, 153], "population": 15200000, "region": "south_america"}, + {"name": "São Paulo", "center": [143, 164], "population": 22400000, "region": "south_america"}, - {"name": "Lagos", "center": [120, 262], "population": 15400000, "region": "africa"}, - {"name": "Kinshasa", "center": [124, 270], "population": 15600000, "region": "africa"}, - {"name": "Cairo", "center": [97, 286], "population": 21300000, "region": "africa"}, - {"name": "Johannesburg", "center": [156, 279], "population": 6000000, "region": "africa"}, - {"name": "Nairobi", "center": [128, 293], "population": 5100000, "region": "africa"}, + {"name": "Cairo", "center": [97, 286], "population": 21300000, "region": "africa"}, - {"name": "Tehran", "center": [92, 308], "population": 9000000, "region": "west_asia"}, - {"name": "Baghdad", "center": [94, 303], "population": 8100000, "region": "west_asia"}, - {"name": "Riyadh", "center": [103, 304], "population": 7700000, "region": "west_asia"}, - {"name": "Ankara", "center": [87, 284], "population": 5700000, "region": "west_asia"}, - {"name": "Karachi", "center": [103, 327], "population": 16500000, "region": "west_asia"}, + {"name": "Tokyo", "center": [92, 400], "population": 37400000, "region": "east_asia"}, + {"name": "Delhi", "center": [99, 339], "population": 32900000, "region": "east_asia"}, + {"name": "Beijing", "center": [87, 383], "population": 21500000, "region": "east_asia"}, - {"name": "Tokyo", "center": [92, 400], "population": 37400000, "region": "east_asia"}, - {"name": "Delhi", "center": [99, 339], "population": 32900000, "region": "east_asia"}, - {"name": "Shanghai", "center": [97, 387], "population": 28500000, "region": "east_asia"}, - {"name": "Beijing", "center": [87, 383], "population": 21500000, "region": "east_asia"}, - {"name": "Mumbai", "center": [107, 333], "population": 21700000, "region": "east_asia"}, - - {"name": "Jakarta", "center": [120, 374], "population": 34500000, "region": "fill"}, - {"name": "Dhaka", "center": [103, 351], "population": 23000000, "region": "fill"}, - {"name": "Manila", "center": [109, 388], "population": 14400000, "region": "fill"}, - {"name": "Bangkok", "center": [109, 370], "population": 11000000, "region": "fill"}, - {"name": "Seoul", "center": [90, 393], "population": 9800000, "region": "fill"}, - {"name": "Osaka", "center": [93, 398], "population": 19300000, "region": "fill"}, - {"name": "Chongqing", "center": [97, 375], "population": 17000000, "region": "fill"}, - {"name": "Kolkata", "center": [103, 349], "population": 15100000, "region": "fill"}, - {"name": "Lahore", "center": [97, 336], "population": 14000000, "region": "fill"}, - {"name": "Shenzhen", "center": [104, 382], "population": 13400000, "region": "fill"}, - {"name": "Bangalore", "center": [111, 339], "population": 13200000, "region": "fill"}, - {"name": "Ho Chi Minh City", "center": [113, 374], "population": 9300000, "region": "fill"}, - {"name": "Luanda", "center": [132, 268], "population": 9000000, "region": "fill"}, - {"name": "Addis Ababa", "center": [119, 292], "population": 5500000, "region": "fill"}, - {"name": "Santiago", "center": [147, 137], "population": 7000000, "region": "fill"}, - {"name": "Taipei", "center": [103, 388], "population": 7000000, "region": "fill"}, - {"name": "Hong Kong", "center": [104, 382], "population": 7500000, "region": "fill"}, - {"name": "Singapore", "center": [119, 372], "population": 5900000, "region": "fill"}, - {"name": "Sydney", "center": [161, 421], "population": 5300000, "region": "fill"}, - {"name": "Casablanca", "center": [93, 249], "population": 3800000, "region": "fill"} + {"name": "Singapore", "center": [119, 372], "population": 5900000, "region": "southeast_asia"}, + {"name": "Lagos", "center": [119, 263], "population": 15000000, "region": "africa"} ] } } diff --git a/tooling/planet-gen/sol_name_fixes.py b/tooling/planet-gen/sol_name_fixes.py index 0b5d0f76b..e33c61fc6 100644 --- a/tooling/planet-gen/sol_name_fixes.py +++ b/tooling/planet-gen/sol_name_fixes.py @@ -4,7 +4,12 @@ sol_name_fixes.py — Name previously-unnamed Sol body auto-detected features. Targets features with null names: Earth oceans/rivers, Luna/Mars/Europa mountain ranges. All names are real-world geographic names for Sol bodies. + +Usage: + python3 sol_name_fixes.py # apply all fixes + python3 sol_name_fixes.py --dry-run # print planned changes without writing """ +import argparse import json from pathlib import Path @@ -44,7 +49,6 @@ FIXES = { "range_579": "Haemus Montes", # 33 cells — south of Mare Serenitatis "range_231": "Gruithuisen Domes", # 25 cells — volcanic domes "range_580": "Mons La Hire", # 25 cells — volcanic dome, Mare Imbrium - "range_606": "Montes Riphaeus", # fallback ID "range_570": "Montes Riphaeus", # 24 cells — Oceanus Procellarum ridge "range_596": "Montes Secchi", # 24 cells — east of Mare Fecunditatis "range_604": "Montes Spitzbergen", # 24 cells — isolated massif @@ -79,7 +83,22 @@ SECTION_MAP = { } -def apply_sol_fixes(): +def _check_dedup(fixes: dict) -> None: + """Raise if any name is assigned to more than one feature ID within a body.""" + for body_id, sections in fixes.items(): + for section, id_map in sections.items(): + seen: dict[str, str] = {} + for fid, name in id_map.items(): + if name in seen: + raise ValueError( + f"Duplicate name {name!r} in {body_id}/{section}: " + f"{seen[name]} and {fid} both assigned" + ) + seen[name] = fid + + +def apply_sol_fixes(dry_run: bool = False) -> None: + _check_dedup(FIXES) for body_id, body_fixes in FIXES.items(): path = WIKI / body_id / "markers.json" if not path.exists(): @@ -99,17 +118,30 @@ def apply_sol_fixes(): new = id_map[fid] if old != new: print(f" [{body_id}/{section}] {fid}: {old!r} → {new!r}") - feature["name"] = new + if not dry_run: + feature["name"] = new changed = True if changed: - with open(path, "w") as f: - json.dump(markers, f, indent=2) - print(f" Written: {path}") + if dry_run: + print(f" (dry-run) Would write: {path}") + else: + with open(path, "w") as f: + json.dump(markers, f, indent=2) + print(f" Written: {path}") else: print(f" No changes for {body_id}") print() if __name__ == "__main__": - apply_sol_fixes() + parser = argparse.ArgumentParser( + description="Name previously-unnamed Sol body auto-detected features." + ) + parser.add_argument( + "--dry-run", + action="store_true", + help="print planned changes without writing any files", + ) + args = parser.parse_args() + apply_sol_fixes(dry_run=args.dry_run) diff --git a/wiki/star-systems/GJ-0/bodies/GJ0d/markers.json b/wiki/star-systems/GJ-0/bodies/GJ0d/markers.json index 0e4fa639d..53b12cd8c 100644 --- a/wiki/star-systems/GJ-0/bodies/GJ0d/markers.json +++ b/wiki/star-systems/GJ-0/bodies/GJ0d/markers.json @@ -48,7 +48,7 @@ }, { "id": "river_1", - "name": "Dnieper", + "name": null, "path": [ [ 59, @@ -266,7 +266,7 @@ }, { "id": "river_4", - "name": "Tone River", + "name": null, "path": [ [ 87, @@ -742,7 +742,7 @@ }, { "id": "river_10", - "name": "Cagayan", + "name": null, "path": [ [ 102, @@ -810,7 +810,7 @@ "oceans": [ { "id": "water_1", - "name": "The World Ocean", + "name": null, "kind": "ocean", "center": [ 125, @@ -837,13 +837,13 @@ "roads": [], "cities": [ { - "id": "city_london", - "name": "London", + "id": "city_brussels", + "name": "Brussels", "center": [ - 79, - 260 + 80, + 266 ], - "population": 9000000 + "population": 2100000 }, { "id": "city_istanbul", @@ -927,13 +927,13 @@ "population": 5900000 }, { - "id": "city_sydney", - "name": "Sydney", + "id": "city_lagos", + "name": "Lagos", "center": [ - 161, - 421 + 119, + 263 ], - "population": 5300000 + "population": 15000000 } ], "railroads": [], diff --git a/wiki/star-systems/GJ-380/bodies/GJ380c/markers.json b/wiki/star-systems/GJ-380/bodies/GJ380c/markers.json index 1e5a7e195..bf4db6e3a 100644 --- a/wiki/star-systems/GJ-380/bodies/GJ380c/markers.json +++ b/wiki/star-systems/GJ-380/bodies/GJ380c/markers.json @@ -52,7 +52,7 @@ }, { "id": "river_1", - "name": "The Kesset", + "name": "Nkwanta Beck", "path": [ [ 250, @@ -253,7 +253,7 @@ }, { "id": "range_5", - "name": "Holt Spur", + "name": "Bosomtwe Spur", "center": [ 33, 396