Skip to content

feat(v3): Phase 1.5 MethodEmitTemplate higher-order rows - #1227

Merged
briansrls merged 12 commits into
mainfrom
phase15-method-emit-template
Apr 30, 2026
Merged

briansrls merged 12 commits into
mainfrom
phase15-method-emit-template

Conversation

@briansrls

@briansrls briansrls commented Apr 29, 2026 •

Copy link
Copy Markdown
Contributor

Summary

  • Add MethodEmitTemplate as the emit-side sum for single-template vs Rust higher-order method templates.
  • Wrap existing Rust/Python/Go MethodTemplateContract.emit_template values as SingleTemplate.
  • Add Rust filter, any, all, and flat_map rows with HigherOrderTemplates, preserving legacy inline_template, fn_ref_template, and wraps_in_sharing values from dsl/extdeps/languages/rust/emit.dag.
  • Add focused coverage for the sum-shaped field, anti-optional/anti-bridge contract fields, and the four Rust higher-order rows.
  • Refresh the parse corpus manifest for the changed .dag surfaces.

Local verification

  • cargo run -p v3-compiler --features bootstrap-regen-fresh --bin regen_bootstrap
  • cargo run -p v3-compiler --features bootstrap-regen-fresh --bin regen_bootstrap -- --verify
  • cargo test -p v3-compiler refresh_handwritten_parse_snapshot_manifest -- --ignored --nocapture
  • cargo test -p v3-compiler --test integration handwritten_parse_snapshot_matches_manifest -- --nocapture
  • cargo test -p v3-compiler --test integration method_template_contract_test -- --nocapture
  • cargo fmt --all --check

Notes

  • dsl/extdeps/languages/rust/emit.dag is untouched except as the source for copied row content.
  • No Grounding row retirement, MethodTranslation / SimpleMethodSpec retirement, or §6a MethodContract cost-shape changes are included.

@briansrls

Copy link
Copy Markdown
Contributor Author

Manager review: the MethodEmitTemplate sum shape is the right direction, and the coproduct receipt in emit_model.dag is much better than the abandoned #1204 branch.

This PR is not yet complete for the dispatched Phase 1.5 acceptance:

  • The four Rust higher-order rows (all, any, filter, flat_map) must be present in rust_method_template_contracts using HigherOrderTemplates, preserving the legacy inline_template, fn_ref_template, and wraps_in_sharing values from dsl/extdeps/languages/rust/emit.dag.
  • Add focused coverage that those four rows are no longer omitted.
  • Add anti-optional/anti-bridge coverage proving MethodTemplateContract did not grow nullable dual-template fields.
  • Include regen/snapshot updates if required by the substrate changes.
  • Retitle/body should describe the actual Phase 1.5 work before this leaves draft.

Please keep the old dsl/extdeps/languages/rust/emit.dag authority untouched except as the copied source for those four row values. Grounding owns retirement.

— sent from jolly-ram-908

@briansrls briansrls left a comment

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Review metadata

  • Provider / model: codex / unknown
  • Commit: 81dd85de · Trigger: schedule
  • Thinking: 157s wall

BLOCKING (1)

Root Cause

  • src/v3/std/rust_method_template_contracts.dag v3 Rust method-template authority still contains only the simple rows while the higher-order facts remain solely in dsl/extdeps/languages/rust/emit.dag → add filter/any/all/flat_map MethodTemplateContract rows with HigherOrderTemplates payloads, or keep the omission receipt until that handoff actually lands.

Non-blocking — Strengths

  • src/v3/std/emit_model.dag MethodEmitTemplate is the right substrate direction for preserving the inline-template versus function-reference distinction instead of collapsing it into a lossy string.

⚠️ One blocking fact-flow gap remains: the PR declares the higher-order Rust rows landed, but the rows are not actually present.

// cross-manager question — flagged at the brief level for
// jolly-ram-908. Same deferral shape as `string_contains`.
// PHASE 1.5 HIGHER-ORDER ROWS:
// - `all` / `any` / `filter` / `flat_map` now use

This comment was marked as resolved.

@briansrls briansrls changed the title eager-ram-167 feat(v3): Phase 1.5 MethodEmitTemplate higher-order rows Apr 29, 2026
@briansrls
briansrls marked this pull request as ready for review April 29, 2026 20:16
@briansrls

Copy link
Copy Markdown
Contributor Author

Review metadata

  • Provider / model: cursor / composer-2
  • Commit: 89ff3f93 · Trigger: schedule
  • Comparison: origin/main @ b5344cad ... review/pr-1227-89ff3f93 @ 89ff3f93
  • Thinking: 63s wall

Verdict: APPROVE

The reviewed change introduces MethodEmitTemplate as a sum (SingleTemplate | HigherOrderTemplates), switches MethodTemplateContract.emit_template to that carrier, updates Go/Python/Rust contract rows to use SingleTemplate { template: ... }, and adds Rust higher-order rows with HigherOrderTemplates plus integration tests that assert the shape, variant names, and absence of parallel nullable fields on MethodTemplateContract. emit_model.dag includes a TERMINAL coproduct classification with a written ledger of why other dissolution patterns do not apply, which matches docs/modeling-discipline.md (coproduct classification for new substrate sums). The tests directly enforce P2-style “no duplicate authority” for the higher-order facts (forbidden field names) and keep per-target dag_method uniqueness. Nothing in the diff contradicts INVARIANTS.md, CODING.md, or TESTING.md in a way that calls for a blocking or non-blocking code finding; the large bootstrap_generated*.rs churn is the expected regen from the .dag edits.

Exploratory (optional, non-finding under your diff-only rule): The file-level //! header above the tests still describes an older “type only / row population is follow-up” story; that narrative is not updated in this diff’s hunks, so it is out of scope for a cited finding but may be worth a quick doc pass in a follow-up if you care about comment–reality alignment.

@briansrls

Copy link
Copy Markdown
Contributor Author

Review metadata

  • Provider / model: openai-pro / gpt-5-5-thinking
  • Commit: 89ff3f93 · Trigger: manual
  • Comparison: main @ b5344cad ... phase15-method-emit-template @ 89ff3f93
  • Conversation: View conversation

1. Story of the diff

This PR turns MethodTemplateContract.emit_template from a raw String into a typed MethodEmitTemplate sum in src/v3/std/emit_model.dag:345-400, with SingleTemplate preserving the existing one-string case and HigherOrderTemplates carrying Rust’s dual inline/function-reference template plus wraps_in_sharing. It then rewrites all existing Go/Python/Rust rows to wrap their prior string templates as SingleTemplate, and adds Rust rows for filter_method, any_method, all_method, and flat_map_method using HigherOrderTemplates at src/v3/std/rust_method_template_contracts.dag:133-172. The test changes in method_template_contract_test.rs check the schema shape, reject nullable/parallel bridge fields, and assert those four Rust higher-order rows are present as HigherOrderTemplates. The large bootstrap_generated*.rs churn appears to be regenerated fixture output reflecting the new declarations and row values, not separate hand-authored logic.

2. Invariant categories

  1. LAYER MODEL (substrate vs implementation).

Finding — Boundary Discipline / E-6, BLOCKING. src/v3/std/rust_method_template_contracts.dag:38 says, “This file is the v3-side row authority,” and src/v3/std/emit_model.dag:400 changes the target-spec row contract to emit_template: MethodEmitTemplate, but the diff does not add or update a generated/product consumer that reads SingleTemplate vs HigherOrderTemplates; the same-PR consumer is a hand-written integration test (src/v3/compiler/tests/integration/method_template_contract_test.rs:265-333) that walks bootstrap FieldValues. For target-spec boundary facts, the invariant bar is that declaration + realization are not enough; a boundary counts as landed when generated compiler code consumes the declared surface, and E-6 says a target-spec field is real only when a consumer lands with it. chatgpt-review-7e3d7c4d-0a91-42…

chatgpt-review-7e3d7c4d-0a91-42…

As written, the PR successfully stages the model, but overclaims it as the v3 row authority before the emitter/grounding consumer exists.

  1. INVARIANTS.md + modeling-discipline.md.

Compliant. The new MethodEmitTemplate avoids nullable bridge fields and makes the ordinary-vs-higher-order state explicit at src/v3/std/emit_model.dag:359-365; the checkpoint comment at src/v3/std/emit_model.dag:345-358 also records the coproduct classification and dissolution attempts expected for a new multi-variant model shape. chatgpt-review-e4a3652b-5c3b-4e…

  1. CODING.md.

Compliant. The Rust additions are test-local free helper functions (conj_field_ty, method_ref_decl_from_row, method_emit_template_variant_label, rust_method_template_rows) rather than new production object/method surfaces, and their panic!/expect usage is confined to tests rather than library code.

  1. TESTING.md.

Compliant. The PR adds focused structural tests for the changed contract: method_template_contract_emit_template_uses_sum_not_nullable_bridge_fields checks the carrier and forbids the rejected nullable/parallel-field shape at src/v3/compiler/tests/integration/method_template_contract_test.rs:112-150, and rust_higher_order_method_template_contracts_are_present checks the four Rust higher-order rows at src/v3/compiler/tests/integration/method_template_contract_test.rs:265-333. These are hermetic/bootstrap-graph assertions rather than external integration flows, and they pin the contract surface rather than generated declaration ordering. chatgpt-review-ea8930ea-b663-47…

  1. LOCKED DESIGN DECISIONS.

N/A — I did not see this diff reference or alter a locked thesis/design decision directly; the relevant concern is the general target-spec consumer rule covered above, not a named locked-design divergence.

  1. TRACKED vs UNTRACKED DEBT.

Compliant, with the same caveat as category 1. The new sum carrier includes a terminal classification ledger in src/v3/std/emit_model.dag:345-358, and the remaining legacy v2 table is explicitly bounded by “until Grounding retires it” at src/v3/std/rust_method_template_contracts.dag:38-39. The unresolved issue is not an undocumented scaffold; it is that the PR labels the v3 rows as authority before landing a generated/product consumer.

3. Verdict

REQUEST_CHANGES. The model shape is directionally good and the tests are useful, but this PR changes a target-spec contract and adds higher-order row data without landing the generated/product consumer that makes that boundary real. I would re-review positively if the PR either adds the consumer for MethodEmitTemplate or downgrades the wording/scope so this is clearly staged data rather than the landed v3 row authority.

@briansrls

Copy link
Copy Markdown
Contributor Author

Review metadata

  • Provider / model: claude / claude-opus-4-7
  • Commit: 7b8dc91c · Trigger: schedule
  • Comparison: origin/main @ 1b9a840b ... review/pr-1227-7b8dc91c @ 7b8dc91c
  • Thinking: 26s wall

Verdict: APPROVE

The diff cleanly resolves the Phase-1 deferral: emit_template: String becomes a MethodEmitTemplate coproduct with SingleTemplate / HigherOrderTemplates variants, preserving the inline-vs-fn-ref distinction without polluting MethodTemplateContract with nullable parallel fields. The type doc comment at src/v3/std/emit_model.dag:348-365 explicitly walks through and rejects the merge / sibling-carrier / collapse alternatives — exactly the modeling-discipline shape the rubric asks for, and the four Rust higher-order rows now attach via the new variant rather than the legacy parallel table. The new test method_template_contract_emit_template_uses_sum_not_nullable_bridge_fields (method_template_contract_test.rs:113-148) locks in the "no nullable bridge fields" invariant against future regression, and rust_higher_order_method_template_contracts_are_present checks the four expected rows. The legacy rust_higher_order_methods table is kept for v2 with a noted retirement trigger ("until Grounding retires it") — tracked, not dangling. Generated bootstrap churn is mechanical.

Nothing in this diff violates INVARIANTS / modeling-discipline / CODING / TESTING.

@briansrls

Copy link
Copy Markdown
Contributor Author

Review metadata

  • Provider / model: openai-pro / gpt-5-5-thinking
  • Commit: 7b8dc91c · Trigger: manual
  • Comparison: main @ 1b9a840b ... phase15-method-emit-template @ 7b8dc91c
  • Conversation: View conversation

1. Story of the diff

This PR replaces MethodTemplateContract.emit_template from a single String with a substrate-level MethodEmitTemplate sum that distinguishes ordinary one-template method emission from Rust’s higher-order method emission shape, where inline-lambda and function-reference templates are separate facts (src/v3/std/emit_model.dag:348-368, src/v3/std/emit_model.dag:403). The Go and Python row tables are mechanically migrated into SingleTemplate { template: ... }, while Rust also adds the previously omitted filter, any, all, and flat_map rows using HigherOrderTemplates so the inline/fn-ref split and wraps_in_sharing bit are carried structurally (src/v3/std/rust_method_template_contracts.dag:133-172). The generated bootstrap files then reflect the updated .dag substrate/data, and the integration test adds ratchets that the contract field points at the sum carrier, does not grow nullable bridge fields, and that the four Rust higher-order rows are present as the higher-order variant (src/v3/compiler/tests/integration/method_template_contract_test.rs:113-150, src/v3/compiler/tests/integration/method_template_contract_test.rs:265-329).

2. Invariant categories

  1. LAYER MODEL (substrate vs implementation). Compliant — this does touch substrate/data modeling in emit_model.dag, and the load-bearing change makes the higher-order case explicit as MethodEmitTemplate = SingleTemplate | HigherOrderTemplates instead of widening MethodTemplateContract with nullable side fields (src/v3/std/emit_model.dag:348-368, src/v3/std/emit_model.dag:403).
  2. INVARIANTS.md + modeling-discipline.md. Compliant — illegal states / single authority are handled by putting the ordinary-vs-higher-order distinction in one emit_template carrier, and the test explicitly rejects parallel nullable fields such as inline_template, fn_ref_template, and emit_template_fn_ref on MethodTemplateContract (src/v3/compiler/tests/integration/method_template_contract_test.rs:137-147). The coproduct is also classified with a terminal ledger explaining why optional fields, sibling carriers, and one-string collapse were rejected (src/v3/std/emit_model.dag:348-361).
  3. CODING.md. Compliant — the Rust additions are free helper functions over explicit inputs (&Dag, &FieldValue) rather than new object behavior, e.g. conj_field_ty, method_ref_decl_from_row, and rust_method_template_rows (src/v3/compiler/tests/integration/method_template_contract_test.rs:36-50, src/v3/compiler/tests/integration/method_template_contract_test.rs:211-263). The new production-facing material is declarative .dag data, not hidden-state Rust logic.
  4. TESTING.md. Compliant — the added tests are behavior/contract ratchets at the right level for a generated bootstrap/std contract: one test checks the shape of MethodTemplateContract.emit_template and absence of bridge fields (src/v3/compiler/tests/integration/method_template_contract_test.rs:113-150), and one checks the four Rust higher-order rows plus their variant/payload shape (src/v3/compiler/tests/integration/method_template_contract_test.rs:265-329).
  5. LOCKED DESIGN DECISIONS. N/A — I do not see this diff referencing or altering a locked thesis/design decision; it extends the live method-template model and regenerates bootstrap artifacts.
  6. TRACKED vs UNTRACKED DEBT. Compliant — the new coproduct is marked terminal, not a scaffold, with a written dissolution/terminal rationale (src/v3/std/emit_model.dag:348-361). The only temporary coexistence called out is bounded to the pre-existing v2 legacy table until Grounding retires it, while declaring this file as the v3-side row authority (src/v3/std/rust_method_template_contracts.dag:33-39).

3. Verdict

APPROVE. The PR moves the missing higher-order Rust method template shape into the substrate/data model instead of papering it over with nullable fields or a flattened string, and it adds focused ratchets for both the schema and the four newly represented rows. I did not find a diff-local invariant, coding, or testing issue that warrants comments or changes.

@briansrls

Copy link
Copy Markdown
Contributor Author

Review metadata

  • Provider / model: codex / codex-default
  • Commit: 492382c7 · Trigger: schedule
  • Comparison: origin/main @ 68502045 ... review/pr-1227-492382c7 @ 492382c7
  • Thinking: 170s wall

Verdict: APPROVE

The diff looks clean. The new MethodEmitTemplate sum is documented with a modeling classification, keeps emit_template as the single authority instead of adding nullable parallel fields, and the Rust higher-order rows preserve the legacy inline/fn-ref split explicitly.

Verified with cargo test -p v3-compiler --test integration method_template_contract: 6 passed.

@briansrls briansrls left a comment

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Review metadata

  • Provider / model: codex / unknown
  • Commit: 492382c7 · Trigger: schedule
  • Thinking: 243s wall

Non-blocking — Strengths

  • src/v3/std/emit_model.dag MethodEmitTemplate preserves the simple versus higher-order template split structurally instead of adding nullable bridge fields.
  • src/v3/compiler/tests/integration/method_template_contract_test.rs The added bootstrap tests pin both the MethodTemplateContract field type and the presence of the four Rust higher-order rows.

✅ The prior fact-flow gap is fixed and I found no blocking concerns.

@briansrls

Copy link
Copy Markdown
Contributor Author

Review metadata

  • Provider / model: openai-pro / gpt-5-5-thinking
  • Commit: 492382c7 · Trigger: manual
  • Comparison: main @ 68502045 ... phase15-method-emit-template @ 492382c7
  • Conversation: View conversation

1. Story of the diff

This PR upgrades MethodTemplateContract.emit_template from a raw String into a modeled MethodEmitTemplate sum so the v3 row table can represent both ordinary one-template method emission and Rust’s higher-order dual-template shape without nullable sibling fields. The core modeling move is in src/v3/std/emit_model.dag:348-368, where SingleTemplate and HigherOrderTemplates become explicit cases, and MethodTemplateContract.emit_template now points at that carrier at src/v3/std/emit_model.dag:403.

The per-target row files then migrate every existing Go/Python/Rust simple row into SingleTemplate wrappers, while Rust adds the previously omitted all, any, filter, and flat_map rows using HigherOrderTemplates at src/v3/std/rust_method_template_contracts.dag:133-171. The generated bootstrap DAGs are refreshed to reflect the schema/ID changes, and the integration test expands from “row uniqueness” into explicit shape checks: no nullable/parallel fields on MethodTemplateContract, plus a Rust-specific assertion that the four higher-order rows exist and carry the higher-order variant at src/v3/compiler/tests/integration/method_template_contract_test.rs:111-150 and src/v3/compiler/tests/integration/method_template_contract_test.rs:265-333.

2. Invariant categories

  1. LAYER MODEL (substrate vs implementation).

Compliant — this is substrate/model-layer work, not implementation-only Rust: MethodEmitTemplate is declared as a first-class .dag type at src/v3/std/emit_model.dag:362-368, and MethodTemplateContract.emit_template is retargeted to that modeled carrier at src/v3/std/emit_model.dag:403 rather than adding Rust-local interpretation.

  1. INVARIANTS.md + modeling-discipline.md.

Compliant — Boundary Discipline / single authority is handled by putting the ordinary-vs-higher-order split behind one emit_template field instead of parallel row lists or nullable sibling fields; the comment explicitly rejects sibling-carrier authority at src/v3/std/emit_model.dag:355-356, and the test ratchets against future nullable/parallel fields at src/v3/compiler/tests/integration/method_template_contract_test.rs:137-147. Coproduct discipline is also addressed with a GREEN terminal annotation and attempted dissolution notes at src/v3/std/emit_model.dag:348-361.

  1. CODING.md.

Compliant — the Rust test additions stay in data + free-function style: conj_field_ty is a narrow helper over Dag and field name at src/v3/compiler/tests/integration/method_template_contract_test.rs:36-50, while method_ref_decl_from_row and method_emit_template_variant_label decompose the reflected FieldValue rows without adding new hidden-state objects or methods at src/v3/compiler/tests/integration/method_template_contract_test.rs:211-252. Panics are confined to tests.

  1. TESTING.md.

Compliant — this PR adds behavior-focused integration coverage at the model boundary: method_template_contract_emit_template_uses_sum_not_nullable_bridge_fields pins the structural contract and rejects bridge fields at src/v3/compiler/tests/integration/method_template_contract_test.rs:111-150; rust_higher_order_method_template_contracts_are_present verifies the four Rust higher-order rows and their variant payload shape at src/v3/compiler/tests/integration/method_template_contract_test.rs:265-333. Given this is bootstrap/reflection data rather than a narrow library helper, using the generated bootstrap DAG is an appropriate integration-level test.

  1. LOCKED DESIGN DECISIONS.

N/A — the diff does not cite or alter a locked design decision directly. It changes emit_model.dag and per-target contract rows, but I do not see a diff-line divergence from a locked thesis/design paragraph.

  1. TRACKED vs UNTRACKED DEBT.

Compliant — the only explicit bridge/debt note is bounded: Rust’s file says this row list is now the v3-side authority while the legacy table remains “for v2 until Grounding retires it” at src/v3/std/rust_method_template_contracts.dag:38-39. The new model also avoids introducing nullable bridge fields, and the test guards against that exact regression at src/v3/compiler/tests/integration/method_template_contract_test.rs:137-147.

3. Verdict

APPROVE — the PR converts a known single-string limitation into a typed modeled carrier, migrates all target rows to the new shape, restores the four Rust higher-order rows without collapsing their dual-template semantics, and adds tests that ratchet both the schema and the Rust row content. I did not find a blocking or non-blocking issue that can be tied to a changed diff line.

@briansrls

Copy link
Copy Markdown
Contributor Author

Review metadata

  • Provider / model: codex / codex-default
  • Commit: 7bc6333b · Trigger: schedule
  • Comparison: origin/main @ 8934d656 ... review/pr-1227-7bc6333b @ 7bc6333b
  • Thinking: 137s wall

Verdict: APPROVE

The diff is narrowly scoped: it replaces emit_template: String with the structured MethodEmitTemplate carrier, wraps existing target rows in SingleTemplate, and adds Rust higher-order rows using HigherOrderTemplates. I did not find a concrete violation of the pinned invariants, modeling discipline, coding guide, or testing guide on changed lines.

Verified with cargo test -p v3-compiler --test integration method_template_contract after correcting the package/test target names: 6 passed.

@briansrls

Copy link
Copy Markdown
Contributor Author

Review metadata

  • Provider / model: openai-pro / gpt-5-5-thinking
  • Commit: 7bc6333b · Trigger: manual
  • Comparison: main @ 8934d656 ... phase15-method-emit-template @ 7bc6333b
  • Conversation: View conversation

1. Story of the diff

This PR resolves the Phase 1 gap where MethodTemplateContract.emit_template could only carry a single string even though Rust’s higher-order methods need two distinct emission templates: an inline body template and a function-reference adapter. The core move is to introduce MethodEmitTemplate as a sum carrier in src/v3/std/emit_model.dag:345, with SingleTemplate for ordinary method rows and HigherOrderTemplates for Rust’s all / any / filter / flat_map rows (src/v3/std/rust_method_template_contracts.dag:133, :144, :155, :166). The existing Go/Python rows are mechanically wrapped in SingleTemplate, while the Rust table adds the formerly omitted higher-order rows and documents that this v3 table is now the row authority while the legacy v2 table remains only until Grounding retires it (src/v3/std/rust_method_template_contracts.dag:33-39). The tests then ratchet both the schema shape and the Rust row presence: they assert MethodTemplateContract.emit_template points to MethodEmitTemplate, reject nullable/parallel bridge fields, and verify the four Rust higher-order methods use the HigherOrderTemplates variant (src/v3/compiler/tests/integration/method_template_contract_test.rs:112-150, :262-296).

2. Invariant categories

  1. LAYER MODEL (substrate vs implementation).

Compliant — this does touch substrate/modeling .dag shape: MethodTemplateContract.emit_template changes from String to MethodEmitTemplate at src/v3/std/emit_model.dag:400, and the new carrier makes the ordinary-vs-higher-order distinction structurally explicit instead of smuggling it through nullable sibling fields. That aligns with the modeling rule that enum/sum shapes need explicit classification/ledgering for coproduct discipline. chatgpt-review-35108e9d-001d-47…

  1. INVARIANTS.md + modeling-discipline.md.

Compliant — illegal states are made unrepresentable at the row boundary: ordinary rows must use SingleTemplate { template: ... } and higher-order rows must use HigherOrderTemplates { inline_template, fn_ref_template, wraps_in_sharing } (src/v3/std/emit_model.dag:359-364). The test also explicitly guards against the bad bridge shape by rejecting fields like inline_template, fn_ref_template, and emit_template_fn_ref on MethodTemplateContract itself (src/v3/compiler/tests/integration/method_template_contract_test.rs:137-147). That is the right single-authority/structural-shape move.

  1. CODING.md.

Compliant — the Rust additions are test-only helper functions over explicit inputs, not new object behavior or hidden state: conj_field_ty(dag, name, field) takes a &Dag and returns the field type (src/v3/compiler/tests/integration/method_template_contract_test.rs:36-50), and method_ref_decl_from_row(row, row_context) parses only the row under test (src/v3/compiler/tests/integration/method_template_contract_test.rs:211-237). This follows the data + free-functions style and explicit dependency guidance. chatgpt-review-13a1dd09-734d-44…

  1. TESTING.md.

Compliant — tests are behavior/contract oriented rather than layout-only: method_template_contract_emit_template_uses_sum_not_nullable_bridge_fields pins the public schema contract (src/v3/compiler/tests/integration/method_template_contract_test.rs:112-150), and rust_higher_order_method_template_contracts_are_present pins the four Rust higher-order rows plus the expected variant payload shape (src/v3/compiler/tests/integration/method_template_contract_test.rs:262-296). The names read as contract claims, consistent with the testing naming discipline. chatgpt-review-a5301213-7f2b-4d…

  1. LOCKED DESIGN DECISIONS.

N/A — I did not see this diff alter a locked thesis/design decision; it extends the live method-template model and regenerated bootstrap data, but it does not change Arrow.body, target realization ownership, reflection semantics, or another locked decision surface.

  1. TRACKED vs UNTRACKED DEBT.

Compliant — the prior Phase 1 omission is removed rather than expanded: the Rust comment now says the four higher-order methods use MethodEmitTemplate.HigherOrderTemplates, and bounds the remaining legacy table as v2-only “until Grounding retires it” (src/v3/std/rust_method_template_contracts.dag:33-39). The new carrier is not introduced as a temporary scaffold; it is documented as terminal/refinable inside payloads (src/v3/std/emit_model.dag:345-358).

3. Verdict

APPROVE — The PR replaces the lossy single-string method template field with a typed carrier, updates all target rows, adds the Rust higher-order rows that were previously omitted, and adds direct contract tests for the new schema and row shape. I did not find a concrete blocking or non-blocking defect in the diff.

@briansrls briansrls left a comment

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Review metadata

  • Provider / model: codex / unknown
  • Commit: 7bc6333b · Trigger: schedule
  • Thinking: 154s wall

✅ The higher-order template facts now flow into the v3 MethodTemplateContract authority and I found no blocking concerns.

@briansrls

Copy link
Copy Markdown
Contributor Author

Review metadata

  • Provider / model: claude / claude-opus-4-7
  • Commit: 19e73912 · Trigger: schedule
  • Comparison: origin/main @ 8934d656 ... review/pr-1227-19e73912 @ 19e73912
  • Thinking: 22s wall

Verdict: APPROVE — Clean, narrowly scoped substrate change.

The diff replaces MethodTemplateContract.emit_template: String with a MethodEmitTemplate Disj (SingleTemplate | HigherOrderTemplates) on src/v3/std/emit_model.dag:367, and migrates all three per-target row tables. The new type's doc-comment explicitly walks through the nullable-fields / sibling-carrier / collapsed-string alternatives and rejects them — exactly the modeling-discipline framing INVARIANTS.md asks for, and the new test method_template_contract_emit_template_uses_sum_not_nullable_bridge_fields (method_template_contract_test.rs:113) actively guards against the rejected patterns. The Phase-1 omission comment in rust_method_template_contracts.dag is dissolved and the four higher-order rows (all/any/filter/flat_map) land with a behavior-driven test that asserts variant choice and placeholder preservation. Generated bootstrap and corpus manifest hashes update consistently. No findings.

@briansrls

Copy link
Copy Markdown
Contributor Author

Review metadata

  • Provider / model: openai-pro / gpt-5-5-thinking
  • Commit: 19e73912 · Trigger: manual
  • Comparison: main @ 8934d656 ... phase15-method-emit-template @ 19e73912
  • Conversation: View conversation

1. Story of the diff

This PR turns MethodTemplateContract.emit_template from a single String into a modeled sum, MethodEmitTemplate, so the v3 method-template table can represent both ordinary single-template methods and Rust higher-order methods that require distinct inline-lambda and function-reference templates. The load-bearing substrate change is in src/v3/std/emit_model.dag:348-368, where the new SingleTemplate | HigherOrderTemplates carrier is introduced with an explicit terminal-coproduct ledger, and src/v3/std/emit_model.dag:403, where MethodTemplateContract.emit_template now points to that carrier instead of String.

The per-target row files then migrate existing Go/Python/Rust rows into SingleTemplate, while Rust adds the previously omitted filter, any, all, and flat_map rows using HigherOrderTemplates at src/v3/std/rust_method_template_contracts.dag:133-172. The generated bootstrap files and parse corpus manifest are refreshed to reflect the new declarations and row bodies. The integration tests add shape checks that prevent regression back to nullable/parallel fields and assert that the four Rust higher-order rows are present and use the higher-order variant at src/v3/compiler/tests/integration/method_template_contract_test.rs:112-150 and src/v3/compiler/tests/integration/method_template_contract_test.rs:268-333.

2. Invariant categories

  1. LAYER MODEL (substrate vs implementation). Compliant — this touches substrate/model data, not just implementation Rust, and the substrate modeling is explicit: MethodEmitTemplate is declared as the single carrier for the two legal method-emission template shapes at src/v3/std/emit_model.dag:362-368, and MethodTemplateContract.emit_template now refers to that carrier at src/v3/std/emit_model.dag:403. That makes the ordinary-vs-higher-order distinction structural rather than a string convention.
  2. INVARIANTS.md + modeling-discipline.md. Compliant — illegal states unrepresentable / single authority are handled by replacing the prior single String with a sum carrier and by rejecting nullable sibling fields in the test at src/v3/compiler/tests/integration/method_template_contract_test.rs:137-149. The new coproduct also carries the required classification/ledger comment for a new multi-variant model at src/v3/std/emit_model.dag:348-361, matching the modeling rubric that new coproducts need a classification and dissolution reasoning. chatgpt-review-80d72fc4-2c85-4e…
  3. CODING.md. Compliant — the new Rust is test-only helper code organized as free functions over explicit &Dag / FieldValue inputs, for example conj_field_ty at src/v3/compiler/tests/integration/method_template_contract_test.rs:36-50 and method_ref_decl_from_row at src/v3/compiler/tests/integration/method_template_contract_test.rs:211-237. That follows the project’s data + functions / explicit dependency style rather than adding object behavior or hidden state. chatgpt-review-1fa08665-c778-4a…
  4. TESTING.md. Compliant — the added tests are hermetic structural assertions over the generated bootstrap DAG. They pin the published model contract, not incidental declaration ordering: one test verifies that emit_template names MethodEmitTemplate and that no parallel nullable fields exist at src/v3/compiler/tests/integration/method_template_contract_test.rs:112-150; another verifies the Rust higher-order rows and payload shape at src/v3/compiler/tests/integration/method_template_contract_test.rs:268-333. This fits the testing guidance to name interface behavior and assert the structural contract. chatgpt-review-14720b0c-a38b-4b…
  5. LOCKED DESIGN DECISIONS. N/A — the diff does not edit a locked thesis/design document or alter a locked design decision. It updates the live model and generated bootstrap artifacts only.
  6. TRACKED vs UNTRACKED DEBT. Compliant — the prior Phase 1 omission comment is replaced by an explicit Phase 1.5 statement that the Rust higher-order rows now live in the v3 row authority, while the legacy table remains only for v2 until Grounding retires it at src/v3/std/rust_method_template_contracts.dag:33-39. The new coproduct is declared terminal rather than scaffolded, with its no-dissolution-trigger rationale at src/v3/std/emit_model.dag:348-361; I do not see a new untracked TODO/bridge introduced by this diff.

3. Verdict

APPROVE

I found no blocking or non-blocking findings tied to the diff. The PR moves the missing higher-order method-template shape into a single modeled carrier, migrates row data through that carrier, and adds tests that ratchet against both nullable-field drift and missing Rust higher-order rows.

@briansrls briansrls left a comment

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Review metadata

  • Provider / model: codex / unknown
  • Commit: 19e73912 · Trigger: schedule
  • Thinking: 185s wall

Non-blocking — Strengths

  • src/v3/std/emit_model.dag MethodEmitTemplate keeps the ordinary versus dual-template shape explicit without nullable bridge fields.

✅ No blocking concerns in this mixed model/test update.

@briansrls

Copy link
Copy Markdown
Contributor Author

Review metadata

  • Provider / model: cursor / composer-2
  • Commit: 1a74e832 · Trigger: schedule
  • Comparison: origin/main @ ed1bc8d2 ... review/pr-1227-1a74e832 @ 1a74e832
  • Thinking: 200s wall

Verdict: APPROVE — The diff introduces a single sum carrier MethodEmitTemplate (SingleTemplate vs HigherOrderTemplates) in emit_model.dag, switches MethodTemplateContract.emit_template to that type, and threads SingleTemplate { … } through Go/Python and HigherOrderTemplates for the four Rust higher-order methods. That matches boundary discipline and illegal-states unrepresentable (no parallel nullable “bridge” fields) as claimed in the new 🟢 coproduct note and the test that forbids the old field names. Tests add focused integration checks on the reflected bootstrap shape and the Rust row payloads; that is appropriate for substrate list data. Regenerated bootstrap_generated*.rs are the expected mechanical fall-out. I do not see a rubric violation tied to a specific diff hunk.

Findings: None.

Exploratory (optional): rust_higher_order_method_template_contracts_are_present matches string templates with contains for placeholders (method_template_contract_test.rs) — fine as a regression guard, but if those strings drift for non-semantic reasons the test may be brittle; not a policy violation.

@briansrls briansrls left a comment

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Review metadata

  • Provider / model: codex / unknown
  • Commit: 1a74e832 · Trigger: schedule
  • Thinking: 256s wall

Non-blocking — Strengths

  • src/v3/std/emit_model.dag MethodEmitTemplate keeps the ordinary versus higher-order template split typed and avoids nullable bridge fields.
  • src/v3/std/rust_method_template_contracts.dag The higher-order Rust rows preserve the legacy inline/fn-ref template split and wraps_in_sharing bit as structured payloads.

✅ No blocking concerns.

@briansrls
briansrls force-pushed the phase15-method-emit-template branch from 1a74e83 to dc964c0 Compare April 30, 2026 00:44
@briansrls

Copy link
Copy Markdown
Contributor Author

Review metadata

  • Provider / model: cursor / composer-2
  • Commit: 11a7f455 · Trigger: schedule
  • Comparison: origin/main @ 13c399ad ... review/pr-1227-11a7f455 @ 11a7f455
  • Thinking: 116s wall

Verdict: APPROVE — The diff tightens the substrate in the right direction: MethodTemplateContract.emit_template stops being a bare String and becomes a sum (MethodEmitTemplate) so ordinary vs higher-order Rust templates stay one authority without nullable parallel fields. emit_model.dag adds a 🟢 TERMINAL coproduct with an explicit pattern-1–3 ledger, which matches docs/modeling-discipline.md (Practice 4). Per-target .dag rows are updated mechanically to SingleTemplate { … }, and Rust adds HigherOrderTemplates rows with comments that tie them to legacy rust_higher_order_methods and defer v2 retirement to named Grounding work — that reads as bounded tracked debt, not a silent bridge. method_template_contract_test.rs adds structural/bootstrap checks (sum labels, forbidden field names, Rust HO rows) consistent with TESTING.md for contract-level claims on the full bootstrap DAG, matching the file’s existing style.

Regenerated bootstrap_generated*.rs churn is expected from the .dag surface change; nothing in that slice needs a separate rubric call-out without a concrete defect.

Exploratory (optional): Nothing substantive beyond noting that Go/Python higher-order methods remain SingleTemplate while Rust uses HigherOrderTemplates; that is consistent with “one string is enough” on those targets but worth a quick mental check later if emit starts needing dual templates there too.

@briansrls briansrls left a comment

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Review metadata

  • Provider / model: codex / unknown
  • Commit: 11a7f455 · Trigger: schedule
  • Thinking: 258s wall

✅ No blocking concerns in the current diff.

@briansrls

Copy link
Copy Markdown
Contributor Author

Review metadata

  • Provider / model: cursor / composer-2
  • Commit: 7b825082 · Trigger: schedule
  • Comparison: origin/main @ b99aaf2c ... review/pr-1227-7b825082 @ 7b825082
  • Thinking: 85s wall

Findings

None. The substantive diff matches the rubric:

  • docs/modeling-discipline.md (Practice 4 — coproduct / enum classification): MethodEmitTemplate is explicitly classified 🟢 terminal with a short ledger (why patterns 1–3 don’t apply) at src/v3/std/emit_model.dag (new block around the MethodEmitTemplate type).
  • P2 / illegal states: MethodTemplateContract.emit_template moves from a single String to MethodEmitTemplate (SingleTemplate vs HigherOrderTemplates), so the inline vs fn-ref vs wraps bit split is structural, not parallel nullable fields on the contract record.
  • Tests: method_template_contract_emit_template_uses_sum_not_nullable_bridge_fields and rust_higher_order_method_template_contracts_are_present in src/v3/compiler/tests/integration/method_template_contract_test.rs ratchet that shape and the four Rust HO rows — consistent with TESTING.md’s stance on integration tests that pin declared substrate/list contracts (same module’s existing pattern).

bootstrap_generated.rs / bootstrap_generated_without_parse_surface.rs churn is mechanical fallout of the .dag change; nothing in that noise suggests a principle violation without nitpicking generated code.

Verdict

APPROVE — Phase 1.5 narrows the substrate to an explicit sum for method emit templates, documents the 🟢 classification, wires Rust HO rows through HigherOrderTemplates, and adds targeted contract tests. No invariant or doc violations surfaced in the reviewed diff.

@briansrls briansrls left a comment

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Review metadata

  • Provider / model: codex / unknown
  • Commit: 15e2212c · Trigger: schedule
  • Thinking: 445s wall

Non-blocking — Strengths

  • src/v3/std/emit_model.dag MethodEmitTemplate keeps ordinary and dual-template method renderings as a typed sum instead of nullable or parallel bridge fields.
  • src/v3/std/rust_method_template_contracts.dag The added Rust higher-order rows match the legacy higher-order template facts and move them into the v3 MethodTemplateContract row authority.

✅ No blocking concerns.

@briansrls
briansrls force-pushed the phase15-method-emit-template branch from 15e2212 to 44bf4df Compare April 30, 2026 05:26
@briansrls

Copy link
Copy Markdown
Contributor Author

Review metadata

  • Provider / model: claude / claude-opus-4-7
  • Commit: 44bf4dfa · Trigger: schedule
  • Comparison: origin/main @ e34f4528 ... review/pr-1227-44bf4dfa @ 44bf4dfa
  • Thinking: 55s wall

Verdict: APPROVE — clean coproduct introduction, dissolution rationale documented in emit_model.dag:348-362, contract tests forbid the parallel-nullable-field pattern (method_template_contract_test.rs:112-148), and per-target rows updated uniformly. Legacy rust_higher_order_methods retention is a tracked bridge with a named retirement trigger (Grounding).

Exploratory observations (non-blocking):

  • rust_method_template_contracts.dag:108-148: in the four HigherOrderTemplates rows, runtime_template is byte-identical to inline_template. That's a single source duplicated into two fields on the same row — not a parallel representation hazard yet, but if runtime_template is ever consumed independently it could drift. Worth a follow-up question for whoever owns the runtime/emit split: is runtime_template actually meaningful for higher-order rows, or should it be derivable from the MethodEmitTemplate variant?
  • The new MethodEmitTemplate payload still carries raw String templates with placeholder conventions encoded in-string ({param}, {iter}, {inner_iter}, {body}, {arg}). The doc comment correctly anticipates this ("richer typed template-segment substrate refines inside the variant payloads") — flagging only as the natural next dissolution target, not a blocker here.

@briansrls

Copy link
Copy Markdown
Contributor Author

Review metadata

  • Provider / model: claude / claude-opus-4-7
  • Commit: 16e701aa · Trigger: schedule
  • Comparison: origin/main @ dc8a1653 ... review/pr-1227-16e701aa @ 16e701aa
  • Thinking: 77s wall

Findings: none.

Verdict: APPROVE — clean substrate-shape change. MethodEmitTemplate is introduced as a proper Disj (SingleTemplate | HigherOrderTemplates) replacing what would otherwise be parallel nullable fields on MethodTemplateContract, and the type comment in emit_model.dag:348-365 explicitly walks through and rejects the three alternative patterns (optional fields, sibling carrier, single-string collapse) — exactly the modeling-discipline shape the rubric asks for. The previously-deferred Rust all/any/filter/flat_map rows now land via HigherOrderTemplates, dissolving the documented Phase 1 omission, and Go/Python rows are uniformly migrated to SingleTemplate. The new contract tests (method_template_contract_emit_template_uses_sum_not_nullable_bridge_fields, rust_higher_order_method_template_contracts_are_present) lock in both the substrate shape (forbidding the bridge field names) and the row presence — fail-closed in the right direction.

Exploratory observation (non-blocking): the higher-order Rust rows now carry placeholders {param}, {iter}, {body}, {inner_iter} that the existing placeholder_convention: NamedArg enum doesn't enumerate. The contract test only checks string contents, not that the renderer knows these names. Worth confirming the v3 emit path actually consumes HigherOrderTemplates (vs. still reading legacy rust_higher_order_methods) before declaring the bridge dissolved — the file comment says "legacy table remains for v2," which is fine, but a v3 reader is what makes this row authority real.

@briansrls briansrls left a comment

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Review metadata

  • Provider / model: codex / unknown
  • Commit: 44bf4dfa · Trigger: schedule
  • Thinking: 233s wall

BLOCKING (1)

Root Cause

  • src/v3/std/emit_model.dag MethodEmitTemplate was expanded without dissolving or reusing the existing wrapping authority → keep the wrap bit in exactly one place, either row-level or inside the emit-template sum.

⚠️ The higher-order rows themselves look faithful, but the new substrate shape should not land with duplicate wrapping authority.

Comment thread src/v3/std/emit_model.dag Outdated
| HigherOrderTemplates {
inline_template: String
fn_ref_template: String
wraps_in_sharing: Bool

This comment was marked as resolved.

@briansrls

Copy link
Copy Markdown
Contributor Author

CI diagnosis for head 16e701aa: v3 fails only on parse-corpus manifest drift after the rebase.

Failing test:

parse_stage4_prep::handwritten_parse_snapshot_matches_manifest

Rows drifted against the checked-in manifest include current-main substrate files, especially:

src/v3/spec/rust.dag: checked in 147 / 1229942 / cf14... ; expected 144 / 1219155 / e377...
src/v3/std/substrate.dag: checked in 59 / 128739 / 8298... ; expected 57 / 124531 / 9d03...

The MethodEmitTemplate tests themselves pass; this is mechanical manifest refresh after the latest main merge.

Please run and commit:

cargo test -p v3-compiler refresh_handwritten_parse_snapshot_manifest -- --ignored
cargo test -p v3-compiler --test integration parse_stage4_prep::handwritten_parse_snapshot_matches_manifest -- --nocapture
cargo test -p v3-compiler --test integration method_template_contract_test -- --nocapture

No schema/source-shape change requested.

— sent from jolly-ram-908

@briansrls

Copy link
Copy Markdown
Contributor Author

Review metadata

  • Provider / model: cursor / composer-2
  • Commit: 7051d708 · Trigger: schedule
  • Comparison: origin/main @ dc8a1653 ... review/pr-1227-7051d708 @ 7051d708
  • Thinking: 90s wall

Findings: None. The diff introduces MethodEmitTemplate in emit_model.dag with an explicit TERMINAL coproduct classification and a short ledger of why other dissolution patterns were rejected, which matches docs/modeling-discipline.md (practice 4). MethodTemplateContract.emit_template is a single sum-typed field instead of parallel nullable fields, which supports P2 (single authority) and avoids compressing two templates into one string (P1/P3). Rust higher-order rows use HigherOrderTemplates and keep wrapping on wraps_result, with comments tying legacy wraps_in_sharing to that field — no duplicate wrapping bit in the new variant. Go/Python rows consistently wrap prior string templates in SingleTemplate. method_template_contract_test.rs adds structural ratchets (disjunct shape, forbidden field names, Rust HO rows). Regenerated bootstrap_generated*.rs and manifest hashes follow from the .dag change.

Verdict: APPROVE — Scope matches Phase 1.5 (higher-order emit templates); substrate modeling and tests align with the referenced principles; no concrete violations grounded in the diff.

@briansrls

Copy link
Copy Markdown
Contributor Author

CI diagnosis for head 7051d708: this is generated-artifact drift after the wrapping-authority fix.

The hand-authored source now keeps wrapping in one place:

// row-level `wraps_result` remains the single wrapping authority...
type MethodEmitTemplate
  = SingleTemplate { template: String }
  | HigherOrderTemplates {
      inline_template: String
      fn_ref_template: String
    }

and the test expects that two-field variant payload. CI still sees a generated bootstrap where filter_method's HigherOrderTemplates payload has length 3, so the generated snapshot is stale relative to the current .dag source:

method_template_contract_test::rust_higher_order_method_template_contracts_are_present
filter_method: HigherOrderTemplates must carry inline and fn-ref templates only
left: 3
right: 2

There is also parse manifest drift for the same files:

src/v3/std/emit_model.dag checked in: 36 / 68760 / 30bb...
expected: 36 / 69306 / a7eb...
src/v3/std/rust_method_template_contracts.dag checked in: 5 / 109753 / 7b10...
expected: 5 / 114675 / cab1...

Please regenerate from the current .dag source and commit the generated deltas:

cargo run -p v3-compiler --features bootstrap-regen-fresh --bin regen_bootstrap
cargo run -p v3-compiler --features bootstrap-regen-fresh --bin regen_bootstrap -- --verify
cargo test -p v3-compiler refresh_handwritten_parse_snapshot_manifest -- --ignored
cargo test -p v3-compiler --test integration method_template_contract_test -- --nocapture
cargo test -p v3-compiler --test integration parse_stage4_prep::handwritten_parse_snapshot_matches_manifest -- --nocapture

No schema/source-shape change requested. The current source shape addresses the duplicate wrapping-authority review by keeping wraps_result row-level and leaving HigherOrderTemplates as { inline_template, fn_ref_template } only.

— sent from jolly-ram-908

@briansrls

Copy link
Copy Markdown
Contributor Author

Review metadata

  • Provider / model: claude / claude-opus-4-7
  • Commit: e4941171 · Trigger: schedule
  • Comparison: origin/main @ e08a77dc ... review/pr-1227-e4941171 @ e4941171
  • Thinking: 49s wall

Verdict: APPROVE — diff cleanly dissolves the Phase-1 deferral by introducing a closed coproduct (MethodEmitTemplate { SingleTemplate | HigherOrderTemplates }) instead of nullable parallel fields on MethodTemplateContract, preserves wraps_result as the single wrapping authority, and lands a regression test (method_template_contract_emit_template_uses_sum_not_nullable_bridge_fields) that explicitly forbids the parallel-field anti-pattern. The thesis on the new type and the rationale comment in rust_method_template_contracts.dag (lines 33–43) name the dissolution trigger for the legacy rust_higher_order_methods v2 table. Rust higher-order rows for all/any/filter/flat_map (rust_method_template_contracts.dag:101–138) match the legacy inline/fn-ref split with their wraps_result bits preserved as expected by rust_higher_order_method_template_contracts_are_present. No invariant violations observed in the diff.

@briansrls

Copy link
Copy Markdown
Contributor Author

Current #1227 head e49411712ff23ee8231e71c3282556380b766054: the generated/bootstrap mismatch from the prior cycle is fixed. method_template_contract_test::rust_higher_order_method_template_contracts_are_present now passes, and the HigherOrderTemplates payload is the intended 2-field shape.

The remaining v3 failure is only parse_stage4_prep::handwritten_parse_snapshot_matches_manifest for two lines:

  • src/v3/std/emit_model.dag: 68760 / 30bb... -> 69306 / a7ebe...
  • src/v3/std/rust_method_template_contracts.dag: 109753 / 7b10... -> 114675 / cab186...

Narrow fix:

cargo test -p v3-compiler refresh_handwritten_parse_snapshot_manifest -- --ignored
cargo test -p v3-compiler --test integration parse_stage4_prep::handwritten_parse_snapshot_matches_manifest -- --nocapture
cargo test -p v3-compiler --test integration method_template_contract_test -- --nocapture

Commit the manifest delta. No source or bootstrap snapshot change is indicated by this CI run.

— sent from jolly-ram-908 (inbox #1130); reply at #1130

@briansrls

Copy link
Copy Markdown
Contributor Author

Review metadata

  • Provider / model: claude / claude-opus-4-7
  • Commit: 3c38880d · Trigger: schedule
  • Comparison: origin/main @ 1694cce8 ... review/pr-1227-3c38880d @ 3c38880d
  • Thinking: 43s wall

Verdict: APPROVE

The diff cleanly dissolves the legacy SimpleMethodSpec / HigherOrderMethodSpec parallel-representation by introducing MethodEmitTemplate as a coproduct on MethodTemplateContract.emit_template (src/v3/std/emit_model.dag:347-368), preserving the single per-row wrapping authority via the existing wraps_result field (the explicit rationale at :351-353 against carrying a second wrapping bit is exactly right). The four higher-order rust rows (rust_method_template_contracts.dag:99-130) attach to HigherOrderTemplates with both inline and fn-ref templates; the obsoleted PHASE-1 OMISSIONS comment is correctly replaced (:33-41).

Tests are well-targeted at the substrate shape rather than the regenerated bootstrap bytes: method_template_contract_emit_template_uses_sum_not_nullable_bridge_fields (method_template_contract_test.rs:113-148) guards against regression to nullable/parallel fields like inline_template/wraps_in_sharing on the contract; rust_higher_order_method_template_contracts_are_present (:267-321) verifies the four rows use the higher-order variant with the legacy placeholders preserved and wraps_result matching legacy wraps_in_sharing.

No INVARIANTS / modeling-discipline / CODING / TESTING violations grounded in this diff. The bootstrap_generated.rs churn is mechanical regeneration consistent with the .dag changes.

@briansrls briansrls left a comment

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Review metadata

  • Provider / model: codex / unknown
  • Commit: 3c38880d · Trigger: schedule
  • Thinking: 194s wall

✅ The Phase 1.5 substrate shape now carries the higher-order template facts structurally, and I found no new concerns.

@briansrls

Copy link
Copy Markdown
Contributor Author

Review metadata

  • Provider / model: openai-pro / gpt-5-5-thinking
  • Commit: 9246a83b · Trigger: manual
  • Conversation: View conversation

1. Story of the diff

This PR closes the Phase 1 gap where MethodTemplateContract.emit_template could only carry a single string, which forced Rust higher-order methods to stay outside the v3 row authority. The core mechanism is a new MethodEmitTemplate sum in src/v3/std/emit_model.dag:348-368: ordinary target methods use SingleTemplate, while Rust higher-order methods use HigherOrderTemplates with separate inline, function-reference, and sharing fields. MethodTemplateContract.emit_template is then retargeted from String to that carrier at src/v3/std/emit_model.dag:400-403.

The per-target row files are migrated to the new shape: Go and Python wrap existing strings in SingleTemplate, while Rust both wraps ordinary rows and adds the four previously omitted higher-order rows for filter, any, all, and flat_map at src/v3/std/rust_method_template_contracts.dag:133-171. The integration tests ratchet the intended modeling shape by asserting the sum carrier exists, nullable/parallel bridge fields did not appear, and the Rust higher-order rows are present with the higher-order variant payload at src/v3/compiler/tests/integration/method_template_contract_test.rs:113-147 and src/v3/compiler/tests/integration/method_template_contract_test.rs:266-327. The generated bootstrap files and parse corpus manifest are consistent generated fallout from the schema/data changes.

2. Invariant categories

  1. LAYER MODEL (substrate vs implementation).

Compliant — this touches declared .dag model/data, not just local Rust implementation. The new cross-pass contract is modeled as MethodEmitTemplate rather than as ad hoc Rust-side interpretation, and MethodTemplateContract.emit_template has a single typed authority at src/v3/std/emit_model.dag:400-403.

  1. INVARIANTS.md + modeling-discipline.md.

Compliant — illegal states are made unrepresentable: the diff does not add nullable bridge fields such as inline_template/fn_ref_template on every row; it introduces a closed sum with SingleTemplate vs HigherOrderTemplates at src/v3/std/emit_model.dag:362-368. The coproduct annotation is also present and explicit: the comment classifies the sum as terminal and explains why optional fields, sibling carriers, or one-string collapse would lose the structural distinction at src/v3/std/emit_model.dag:348-361.

  1. CODING.md.

Compliant — the Rust additions are test-only helper functions over explicit inputs, not new object behavior or hidden state. For example, conj_field_ty(dag, name, field) -> DeclarationId is a free helper over &Dag at src/v3/compiler/tests/integration/method_template_contract_test.rs:36-50, and the production change itself stays in declarative .dag data.

  1. TESTING.md.

Compliant — the PR adds focused regression coverage for the exact contract it changes. One test pins the schema shape and absence of nullable/parallel bridge fields at src/v3/compiler/tests/integration/method_template_contract_test.rs:113-147; another pins the Rust higher-order row presence and payload shape at src/v3/compiler/tests/integration/method_template_contract_test.rs:266-327. Given this is a bootstrap/generated-Dag contract, using generated_full_bootstrap_dag() is an appropriate integration-level surface rather than an avoidable full-pipeline fixture.

  1. LOCKED DESIGN DECISIONS.

N/A — I do not see the diff altering a locked design document or diverging from a locked substrate/emission decision. The change is additive modeling inside emit_model.dag plus row migration.

  1. TRACKED vs UNTRACKED DEBT.

Compliant — the prior Phase 1 omission block is removed and replaced by landed higher-order rows at src/v3/std/rust_method_template_contracts.dag:25-31. The only remaining bridge language is bounded to the existing v2 legacy table “for v2 until Grounding retires it” at src/v3/std/rust_method_template_contracts.dag:30-31, and the new sum itself explicitly says richer future typed template segments refine inside the variant payloads rather than replacing the carrier at src/v3/std/emit_model.dag:358-361.

3. Verdict

APPROVE — the PR replaces a real modeling gap with a typed single-authority carrier, migrates the target rows through that carrier, and adds direct regression tests against the bridge shapes this could otherwise regress into. I did not find a diff-line-grounded blocker or non-blocking finding.

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