Commit Graph

182 Commits

Author SHA1 Message Date
1f39ec709e Merge client canon log engine (Plan B)
Client-side GDScript engine that constructs the canon log at new-game
(origin + world + character creation) and maintains its invariants turn
to turn. Headless GUT-tested logic layer (48 tests): typed RefCounted
model with invariants-in-the-model, Luck-centric GameState, ContentDB
mirroring the api id-resolver, NewGame.construct, and a pure §12 tag
extractor. Binds to the Plan A canon log contract.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-07-09 15:34:41 -05:00
bc83e92f44 chore(client): Godot rewrote project.godot header on open
Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-07-09 15:34:41 -05:00
63ce3efb74 fix(client): reject empty player name in NewGame.construct (contract minLength:1)
Whole-branch review flagged that NewGame.construct validated class and
origin refs but not player.name. The canon-log schema requires
player.name with minLength:1, so a missing/blank name previously
returned ok:true and produced a log the API would reject with 422.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-07-09 15:03:18 -05:00
2d52d74963 chore(client): track generated .uid for test_round_trip.gd
Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-07-09 14:51:48 -05:00
2673126003 test(client): round-trip + contract-invariant integration on a constructed log
Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-07-09 14:51:42 -05:00
5388979bf1 feat(client): TagExtractor — pure regex parse/strip of §12 tags
Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-07-09 14:46:11 -05:00
7c5eaf3ba3 test(client): cover non-companion disposition routing (§6/§7 boundary) in NewGame
Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-07-09 14:42:12 -05:00
8ca89a1ab2 feat(client): NewGame.construct — origin+world+creation -> {canon log, state}
Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-07-09 14:36:50 -05:00
fe03d1f787 feat(client): ContentDB loads /content + mirrors the api id-resolution check
Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-07-09 14:30:48 -05:00
0a9742a984 feat(client): Luck (deterministic gen/drift/descriptor) + GameState store
Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-07-09 14:24:59 -05:00
4166370f9d feat(client): CanonLog container + maintenance mutators (cap 5, dedup, stack)
Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-07-09 14:19:55 -05:00
a682022f17 feat(client): id helper + leaf canon-log entities with owned invariants
Also configure GUT to not treat push_error() as a test failure
(client/.gutconfig.json: failure_error_types = [engine, gut]).
The brief's LogPlayer/Quest setters intentionally push_error() on
rejected input; GUT's default failure_error_types includes
push_error, which would fail test_player_rejects_unknown_class and
test_quest_status_enum despite their assertions passing.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-07-09 14:12:16 -05:00
5486ed00fa chore(client): vendor GUT 9.7.1 + headless test harness 2026-07-09 14:05:20 -05:00
1c5f08c5e7 docs(plan): client canon log engine (Plan B) implementation plan
Eight TDD tasks off feature/client-canon-log-engine: GUT harness, leaf
entities, CanonLog container + mutators, Luck+GameState, ContentDB,
NewGame.construct, TagExtractor, round-trip/contract-invariant bridge.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-07-09 13:58:21 -05:00
5a1f1ac0ca docs(spec): client canon log engine (Plan B) design
The client half of the canon log contract: typed RefCounted model with
invariants-in-the-model, Luck-centric game state, new-game construction
from origin+world+creation, turn-to-turn mutators, and a pure regex tag
extractor. Headless GUT-tested logic layer; UI/HTTP/save-load deferred.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-07-09 13:46:53 -05:00
272995fb6c Merge canon log follow-ups
Sort-key hardening, unified 422 error envelope, starlette warning filter, and
the docs/canon-log.md living contract for the Plan B client.
2026-07-09 13:09:32 -05:00
7f1d9fa39a chore(api): canon log follow-ups — hardening, unified 422, contract doc
- canon_log.py: stringify jsonschema error-path segments before sorting so a
  future schema mixing array indices and object keys can't TypeError (#1)
- main.py: RequestValidationError handler reshapes pydantic body failures into
  the same {"detail": {"canon_log_errors": [...]}} envelope as schema failures,
  so the client parses ONE 422 shape (#2a) + tests
- pytest.ini: filter the starlette/httpx TestClient deprecation → pristine output (#4)
- docs/canon-log.md: living contract for the client (Plan B) — schemas, the §7
  boundary, the unified error envelope, per-role injection (#3)

Full suite 26 passing, 0 warnings.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-07-09 13:03:59 -05:00
0e9d1b2a43 Merge canon log contract & api validation (Plan A)
JSON Schema contract for canon log + origin seeds (single source of truth),
validator module, POC deserter origin + minimal world fixtures with
id-resolution, canon-log validation wired into all five role endpoints
(422 on invalid), and schemas bundled into the Docker image with a passing
runtime smoke test. Full suite 25 passing.
2026-07-09 12:58:44 -05:00
e39d1a446e fix(api): constrain disposition_overrides keys; close docker paper cuts
Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-07-09 12:54:01 -05:00
4ab0e564ef chore(api): bundle canon log schemas into image; repo-root build context
Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-07-09 12:45:49 -05:00
6d5510773a feat(api): validate canon log at every role endpoint (422 on invalid) 2026-07-09 12:42:03 -05:00
4aa65c9d4c feat(content): POC deserter origin + world fixtures with id-resolution check 2026-07-09 12:37:29 -05:00
e80a4071f6 fix(api): pattern-constrain humiliations id; broaden canon log boundary tests 2026-07-09 12:34:31 -05:00
843ab11a5c feat(api): canon log JSON Schema + validator, enforce §7 luck boundary
Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-07-09 12:31:10 -05:00
710745e548 feat(api): origin seed JSON Schema + validator
Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-07-09 12:26:39 -05:00
38c659cbfe Merge canon log schema design + implementation plan
Design spec + Plan A (contract & api validation) + content/world reorg.
2026-07-09 12:22:01 -05:00
87c5748295 docs: implementation plan for canon log contract + api validation
Plan A of two: the JSON Schema contract, authored POC fixtures (deserter
origin + minimal world), and the api's runtime validation of every canon log
(422 on invalid, enforcing the §7 luck boundary). Five TDD tasks, all runnable
with pytest + Docker in-repo. Plan B (GDScript client construction/maintenance)
deferred until we're in Godot.

Plan: docs/superpowers/plans/2026-07-09-canon-log-contract-and-api-validation.md

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-07-09 12:18:41 -05:00
800811dac2 docs: canon log schema + origin seed design
Design spec for the §11 canon log, plus origin seeds as thin initial-state
overlays over a single static world. Three layers (world content / origin seed /
runtime canon log), the in/out boundary (numeric Luck never enters the AI
payload, §7), field-level schemas, new-game construction order, turn-to-turn
maintenance, and JSON storage validated on both client and api.

Folds content/npcs and content/quests under content/world/; adds
content/world/{locations,items} and content/origins. fallback/ kept outside
world/ (authored prose, not id-referenced).

Spec: docs/superpowers/specs/2026-07-09-canon-log-schema-design.md

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-07-09 12:03:37 -05:00
d340e06dad docs: add git workflow to working agreement (§18)
Long-lived master + dev; all non-doc work on branches off dev; doc-only
edits go straight to dev; human owns the dev->master merge and pushes
master; Claude pushes only dev, only after a --no-ff merge.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-07-09 11:27:04 -05:00
c5eccbb2a5 chore: gitignore and untrack .claude harness files
These are Claude Code session/state files, not project code. They were
swept into the first commit; remove from the index (kept on disk) and
ignore going forward so they stop dirtying status.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-07-09 11:24:46 -05:00
d4ada9bedb chore: dockerize api proxy and add gitignore
Add a Docker-based FastAPI proxy skeleton (charter §4) for parity across
dev / homelab VPS / fly.io, plus root .gitignore for Godot 4.7 and Python.

- api/Dockerfile: python:3.12-slim, non-root, PORT-aware CMD
- api/app/main.py: /health + five role endpoint stubs (§4)
- api/requirements.txt: fastapi/uvicorn/httpx/pydantic, pinned
- docker-compose.yml: local dev with live reload
- api/fly.toml: prod deploy stub with /health check
- api/.env.example: key lives in the proxy, never the client (§4)
- .gitignore: ignores .env, whitelists .env.example

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-07-09 11:23:27 -05:00
d54599e27d first commit 2026-07-09 11:17:54 -05:00