Skip to content

Phase 1 / Etch / Structural mutation in bodies#38

Merged
guysenpai merged 15 commits into
mainfrom
phase-1/etch/structural-mutation
Jun 30, 2026
Merged

Phase 1 / Etch / Structural mutation in bodies#38
guysenpai merged 15 commits into
mainfrom
phase-1/etch/structural-mutation

Conversation

@guysenpai

Copy link
Copy Markdown
Contributor

M1.0.10 — Structural mutation in bodies (spawn / despawn / add(T) / remove(T))

Brief: briefs/M1.0.10-structural-mutation.md

The four structural ops are now executable from rule / observer / hook bodies as DEFERRED changes, and the S4 "no structural mutation" interpreter boundary is lifted. Each op enqueues a Tier-0 CommandBuffer command onto world.observer_registry.deferred, drained at the tick boundary via applyWithObservers (observers fire per op), never mid-iterateArchetype. No body handle / sentinel (reserved post-v0.6); command_buffer.zig / entity.zig untouched (FROZEN).

Gate-by-gate

  • E1 — Parser + AST: spawn graduates non_s3_keywordskw_spawn; new ExprKind.spawn_struct (spawn ( structural vs spawn { = fail-loud M1.0.11 async seam). despawn/add/remove need no parser change (postfix methods on an Entity receiver).
  • E2 — Type-checker: the four ops recognized on an Entity receiver; refusals E0304 (body handle unavailable — v0.6 statement-only) / E0305 (prefab spawn not executable Phase 1). Completion (Claude.ai round-trip, VERDICT E2 — STOP): static component-literal field validation E0306 / E0307 by reusing the scene/prefab checkComponentInstance path so weld check (C1.6) catches the same field errors.
  • E3 — Interp: dispatch the four ops to the Tier-0 CommandBuffer (eager payload resolution: component defaults + field overrides via bridge.writeValueAsBytes); flushStructural drain at the tick boundary (after tags + extensions, drain-until-empty for observer cascades); S4 header line lifted.
  • E4CLAUDE.md §3.4: Next planned milestone → M1.0.11, M1.0 = 21 sub-milestones (M1.0.0–M1.0.20), NOT complete (M1.0.0–M1.0.10 closed); Last released tagv0.10.10-structural-mutation; +1 Tags row; +1 open-decision "M1.0.10 scope boundary".

Closing notes

  • What worked: the deferral primitive was reused verbatim (Tier-0 CommandBuffer + applyWithObservers, zero new Tier-0 surface); the M1.0.9 entity-method dispatch site and the scene/prefab field-validation path mirrored cleanly; the gate-by-gate cadence kept each diff small.
  • Deviations: (1) E2 completion adds static field validation (E0306/E0307) — Recorded deviation (3ea6adc). (2) FROZEN E2 prose says "Three refusals" but enumerates + tests two (E0304, E0305); the three value-use sub-cases of (a) are covered by the single E0304 arm — no third refusal invented. (3) Out-of-list files touched (justified in Execution log): token.zig (E1 lexer graduation), diagnostics.zig (E2 new codes). (4) E3 routes via a structuralDeferred helper instead of binding observer_deferred in execBody — equivalent, leaves the tag/extension pending_* paths untouched.
  • Flag in review: Last released tag bumped to v0.10.10 (anticipates the post-merge tag; keeps the invariant "Last released tag == newest Tags row"); the structuralDeferred routing choice; the drain order flushPendingTags → flushPendingExtensions → flushStructural.
  • Final measurements: N/A — correctness milestone (no benchmark per the brief); deferred ops apply once at the tick-boundary drain, no new per-tick hot path.
  • Residual / intentional debt: async spawn { } (M1.0.11, E1 seam diagnostic); prefab-name spawn("X") execution (E0305, post-Etch prefab runtime); no body handle / sentinel (reserved post-v0.6, NOT built); §30.5 additive-conflict cook warning (later cook milestone); entity/enum component-field kinds ride the existing Value→bytes machinery (POD covered by tests).

Validation (all green)

  • All "Scope" deliverables present (E1–E4)
  • No drift to "Out of scope"
  • Acceptance-criteria tests pass in debug + ReleaseSafe
  • Benchmarks — N/A (correctness milestone)
  • Observable behavior demonstrable (interp tests: each op defers + materializes at flush; observers fire per op; B1 multi-entity live walk uncorrupted)
  • zig build, zig build test, zig fmt --check, zig build lint green
  • CLAUDE.md updated (§3.4 current-state line fixed + Tags row + open-decision)
  • Language audit §3.6.1 — no French in the code/comment/brief diff (clean)
  • Drift audit §3.6.1 — grep -rn of modified terms: no orphans (old S4 "No structural mutation" line gone everywhere; spawn_struct + the 4 new diagnostics consistent)
  • Closing notes filled; Status → CLOSED, Closed 2026-06-30

Merge (squash) + tag (v0.10.10-structural-mutation) are Guy's, after review.

🤖 Generated with Claude Code

@guysenpai guysenpai merged commit f367967 into main Jun 30, 2026
16 of 18 checks passed
@guysenpai guysenpai deleted the phase-1/etch/structural-mutation branch June 30, 2026 19:16
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant