Cross-Cutting Review R1 — Tiers 1–3 Authoring¶
Docs reviewed
- Tier 1: tier1-yaml-first-authoring.md
- Tier 2: tier2-ai-content-pipeline.md
- Tier 3: tier3-visual-tools.md
Codebase touchpoints inspected (for reality-checking interfaces)
- Data pipeline: packages/maid-engine/src/maid_engine/loader/phases/{discover,prepare,resolve_refs}.py, loader/models.py, loader/entity_types.py
- CLI: packages/maid-engine/src/maid_engine/cli/app.py (existing maid data …, maid dev generate, maid dev test-ai)
- Admin API: packages/maid-engine/src/maid_engine/api/admin/router.py, packages/maid-stdlib/src/maid_stdlib/api/admin/world.py
0) Executive Summary (system-level)¶
The three tiers share a solid intent (“same pipeline / same validation / multi-surface authoring”), but they currently describe incompatible external interfaces—especially the YAML shape and schema declaration. Tier 2 aligns closely with the current loader implementation (_meta.schema, list/dict collections, components{…}), while Tier 1 describes an author-friendly YAML surface (_schema + top-level name/short_desc/long_desc/extended) that would require additional translation logic that Tier 2 and Tier 3 do not consistently acknowledge.
Tier 3’s YAML import/export example is not pipeline-compatible as written (different document structure, different fields, and a new “area” object). It looks like an API payload format rather than Tier 1 content YAML.
Main architectural gap: “single source of truth” and reconciliation rules (YAML vs live world vs visual editor) are not consistently defined end-to-end.
1) Tier Dependencies¶
1.1 Do tiers build correctly?¶
- Tier 2 → Tier 1: Correct at the conceptual level (“AI output must pass Tier 1 validation”), but Tier 2 implicitly assumes the pipeline YAML format (component-centric) while Tier 1 describes a different authoring format.
- Tier 3 → Tier 1: Correct conceptually (“import/export YAML through Tier 1 pipeline”), but Tier 3’s example YAML is a third format.
- Tier 3 → Tier 2: Tier 3 calls Tier 2 a dependency in the header, but later explicitly states Tier 2 features are optional / degrade gracefully. This should be reflected as an optional dependency.
1.2 Circular dependency risk¶
No explicit circular dependency, but there’s a “soft” coupling loop: - Tier 1 is positioned as canonical authoring. - Tier 2 must emit canonical authoring. - Tier 3 must round-trip canonical authoring.
If Tier 1’s “canonical” format differs from Tier 2/Tier 3 assumptions, the tiers become mutually blocking.
1.3 Can tiers be delivered independently?¶
- Tier 1 can ship alone.
- Tier 2 can ship once Tier 1’s external YAML contract is finalized.
- Tier 3 can ship largely independent of Tier 2 (as the doc claims), but only if Tier 1 YAML import/export and reconciliation semantics are crisp.
Recommendation: Change Tier 3 header to “Depends on Tier 1; integrates with Tier 2 (optional)”.
2) Interface Consistency¶
2.1 DataDrivenContentPack¶
- Tier 1 defines
DataDrivenContentPackas the Tier 1 integration seam. - Tier 2 and Tier 3 largely treat “content packs” generically and add optional methods (Tier 2:
get_ai_prompt_templates; Tier 3:get_editor_extensions).
Issues
- Tier 2 shows adding get_ai_prompt_templates() into ContentPack(Protocol) directly. In the codebase, ContentPack is a strict Protocol. Making it required is a breaking change for all packs.
- Tier 3 uses hasattr(pack, 'get_editor_extensions'), which is consistent with “optional extension methods”. Tier 2 should follow the same approach.
Recommendation: Standardize on optional capabilities (duck-typed) or an explicit “capability registry” to avoid repeatedly extending the Protocol.
2.2 YAML schema declaration (_schema vs _meta.schema)¶
Inconsistency across tiers:
- Tier 1: schema declared at top-level as _schema: maid:room:v1.
- Tier 2: schema declared under _meta.schema: maid:room:v1.
- Current code (PreparePhase) reads schema from _meta.schema and infers from keys/dirs otherwise.
Recommendation: Pick one and make all tiers consistent. Given current implementation, the path of least resistance is:
- Canonical: _meta.schema (and drop _schema in Tier 1 unless the loader is updated).
If Tier 1 strongly prefers _schema for author ergonomics, then Tier 1 must explicitly include a normalization step (“accept _schema as alias for _meta.schema”), and Tier 2/Tier 3 must generate it accordingly.
2.3 YAML entity collection shape (map vs list) and required fields¶
Tier 1 examples primarily show:
- rooms: { village_square: { name: …, short_desc: …, exits: {…} } } (id is the map key)
Tier 2 examples show:
- rooms: [ { _id: …, components: { DescriptionComponent: … } } ] (id inside object)
Current loader code supports both list and map collections, but it fundamentally expects:
- Each entity becomes a dict with _id and components.
Critical mismatch: Tier 1’s author-friendly top-level fields (name, short_desc, extended, npc, etc.) are not part of the current pipeline’s required payload. They would need a translation layer to map to components (e.g., DescriptionComponent). Tier 2’s “schema extraction from components” also implies the component-centric format is canonical.
Recommendation: Decide whether Tier 1’s YAML schema is: 1) The canonical pipeline input (then Tier 2/Tier 3 must output it, and the loader must implement translation), OR 2) A human-friendly authoring syntax that compiles to canonical component YAML (then the translation step and its guarantees must be a first-class Tier 1 interface and referenced everywhere).
2.4 Tier 3 YAML import/export format is a third format¶
Tier 3 export example:
area:
name: …
metadata:
editor_layout: …
rooms:
- id: town_square
description: …
exits:
- direction: north
destination: market_street
area: object
- rooms as a list of {id, description} rather than {_id, components}
- exits as a list rather than the pipeline’s native dict/object conventions
Recommendation: Either:
- Define a formal maid:area:v1 schema and an explicit converter to/from Tier 1 canonical content YAML, or
- Change Tier 3 import/export examples to exactly match Tier 1 canonical format.
2.5 CLI command naming¶
- Tier 1 proposes new
maid data diff/watch/export/init/migrate. - Tier 2 proposes
maid ai …replacingmaid dev generate. - Tier 3 references
maid data load/validate/lintand builder commands like@export.
Risks
- Multiple “export” concepts (Tier 1 maid data export; Tier 3 @export; Tier 3 “Export Selection…” UI).
Recommendation: Create a single CLI naming map and explicitly state: - which commands are offline-only vs connected-to-server - which commands operate on YAML vs on live entities
2.6 API endpoints and WebSocket path consistency¶
Tier 3 contains two conflicting statements:
- Architecture diagram mentions /admin/ws/editor.
- Appendices define editor messages as /admin/ws with channel: "editor".
Current code already has WS /admin/ws.
Recommendation: Use one model:
- Prefer “single WS endpoint, multiple channels” (matches existing infra).
- Remove /admin/ws/editor references or redefine clearly as an alias.
3) Architecture Coherence¶
3.1 Single source of truth¶
Across tiers there are (at least) three candidate “truths”: 1) YAML files in a pack repo (Tier 1) 2) Live world/entity state in the running server (Tier 3) 3) AI-generated drafts staged for approval (Tier 2)
Tier 1 introduces “diff” and provenance concepts; current code already has:
- DataProvenanceComponent (definition hash, source file)
- InstanceStateComponent (runtime modified/dirty tracking)
But the combined system never states the canonical rule: - Is YAML authoritative and live state is derived? - Or is live state authoritative with YAML as an export snapshot? - Or are both first-class with a reconciliation policy?
Recommendation: Write a single cross-tier “Content Source of Truth & Reconciliation” section (owned by Tier 1, referenced by Tier ⅔) that defines: - canonical store (YAML vs runtime) - drift detection triggers - merge policy (e.g., YAML overwrites runtime on reload vs preserve runtime edits) - how visual editor edits are persisted (immediate runtime + later export, or direct YAML writes + reload)
3.2 Multi-surface editing behavior¶
Tier 3 promises changes are visible across surfaces via WebSocket. Tier 1 proposes offline diff/watch.
Missing glue: What happens when:
- YAML is edited in git and reloaded while multiple builders are editing in the visual editor?
- the visual editor modifies entities that were loaded from YAML (provenance exists) and later someone runs maid data diff?
Recommendation: Define a “three-way model”: - Definition (canonical YAML definition) - Instance (runtime entity state) - Edits (changesets / dirty patches)
Then standardize:
- maid data diff compares Definition ↔ Instance
- visual editor writes Edits (patches) and can optionally “materialize to YAML”
4) Mix-and-Match Story¶
4.1 Tier 1 only¶
Achievable: YAML + pipeline + validation. However, the Tier 1 doc’s YAML shape does not match the current loader’s shape, so “Tier 1 only” success requires clarifying and implementing the actual canonical YAML format.
4.2 Tier 2 without Tier 3¶
Plausible (CLI + in-game @ai), but only if Tier 2 emits Tier 1 canonical YAML and shares the same schema/versioning conventions.
4.3 Tier 3 without Tier 2¶
Doc claims this is possible (AI buttons disabled). That’s coherent, but only if Tier 3 uses Tier 1 import/export format exactly.
4.4 “Zero Python content pack” promise¶
Tier 1 promises “manifest.toml + data/ only” packs. Tier 3’s pack extension system is necessarily Python/JS, but that’s optional.
Recommendation: Make the promise precise: - “Zero Python is supported for content data packs (rooms/items/npcs/templates).” - “Behavioral extensions and custom editor panels require code.”
5) Implementation Overlap / Conflicts¶
5.1 Balance analysis duplication¶
- Tier 2 includes a Balance Analysis Engine and CLI
maid ai balance …. - Tier 3 proposes
/admin/balance/*endpoints and a Balance Dashboard.
Risk: Two separate balance implementations.
Recommendation: Treat Tier 2’s balance engine as the library, and Tier 3 as the UI/API surface over it.
5.2 “Export” and “changeset” overlap¶
Tier 1 proposes maid data export (export loaded entities to YAML).
Tier 3 proposes changesets + apply, plus YAML import/export.
Recommendation: Decide whether changesets are: - runtime-only collaboration artifacts, or - the authoring equivalent of “git staging” that can be exported as patch/YAML.
6) Missing Glue (cross-tier concerns)¶
6.1 Versioning + source control workflow¶
Tier 1 addresses schema versioning and migrations; Tier 3 mentions CI validation; Tier 2 adds generation metadata.
Missing:
- recommended git workflow (branch-per-change, PR review, CI validate)
- how editor changesets become commits
- whether _meta.generated_by etc should be committed or stripped
6.2 Multi-user ownership and conflict resolution¶
Tier 3 defines locks and review workflow; Tier 1 and Tier 2 do not define ownership.
Missing: - what constitutes “ownership” of a pack / area - how cross-pack references are governed in teams - conflict policy when two changesets touch the same entity
6.3 Testing strategy across tiers¶
Each tier mentions validation/testing locally, but missing an end-to-end strategy: - golden tests for YAML → pipeline → world → YAML round-trip - contract tests ensuring Tier 2 generator outputs pass Tier 1 validation - integration tests for editor import/export fidelity
6.4 Documentation strategy¶
Three tiers risk three overlapping “truths”.
Missing: - one canonical glossary - one canonical “YAML contract” doc - one canonical “admin API authoring contract” doc
6.5 Performance budget across tiers¶
Tier 1: pipeline timeout; Tier 2: token budgets + caching; Tier 3: UI perf and WS batching.
Missing: - combined throughput budget (e.g., “import 1k rooms, validate < N seconds, editor initial load < M seconds, WS update < 100ms”) and how they interact
7) Terminology Consistency¶
Observed drift: - “content pack” vs “pack” vs “plugin” used interchangeably. - “builder” vs “author/creator” used inconsistently. - “area” vs “zone” vs “world graph cluster” appears in Tier 3 export example without a Tier 1 schema.
Recommendation: Adopt a cross-tier glossary:
- Content pack: loadable unit with manifest.toml / ContentPackManifest.
- Data pack: content pack with only YAML data (no code).
- Plugin: reserved for engine/plugin tooling or registry; avoid as synonym for content pack.
- Zone: Tier 1 zone entity type (if that’s the intent).
- Area: if used, define schema and relationship to zone.
- Builder: in-game/editor user. Author: repository/YAML editor.
8) Concrete Alignment Actions (highest leverage)¶
1) Choose and publish a single canonical content YAML contract (schema field, collection shape, component mapping). Then update Tier ½/3 examples to match.
2) Define a formal “Area” concept (or remove it) so Tier 3 import/export is not an undocumented third format.
3) Standardize extension capabilities for packs (get_ai_prompt_templates, get_editor_extensions) as optional duck-typed hooks or a shared capability registry—avoid Protocol churn.
4) Unify WebSocket story: one endpoint + channel routing (or clearly document multiple endpoints).
5) Write the reconciliation rules: YAML vs runtime edits vs changesets, including how maid data diff/export fits into Tier 3 workflows.
9) Open Questions (need cross-tier answers)¶
- Is Tier 1’s author-friendly YAML (no explicit
components) a planned new front-end syntax, or are Tier 2/loader’s component-centric docs the true contract? - What is the intended relationship between
zone(Tier 1) andarea(Tier 3/world API)? - Should visual editor changes be applied to live world immediately, or staged as changesets and only applied on approval?
- How should AI generation metadata be stored so it doesn’t create noisy diffs in git?
End of review.