Repository navigation
record-literal constructor domains: candidates with routes, not one canonical node - #10442
gunbai-bot[bot] wants to merge 1 commit into
Conversation
This is the subject routed out of #10187, restored onto the cleaned head so the child has a concrete starting point rather than a placeholder. It carries the material as it stood when it was extracted -- RecordLitUnavailableCause, the three-way RecordLitInstantiation construction, the Boolean gate, the four-route mask fix, the undetermined diagnostics, and the outer/element variant selection. The selection in this commit is KNOWN TO BE THE WRONG SHAPE and is replaced by the next commits. It resolves outer-versus-element by returning one preferred Node, which is the same defect the repair is for: canonicalization may erase spelling differences, and this erases semantic path. The replacement is an authority returning CANDIDATES WITH ROUTES, with the constructor lookup owning the zero / exactly-one / more-than-one fold. Co-Authored-By: Claude Opus 5 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01HsALPpj3hERxcuCfK6Cc23
|
Superseded by #10473. This branch was cut from #10473 is the same subject reconstructed on The pre-rebuild head of this branch is retained at Note for anyone following a cross-reference: finding 1 was transferred to this PR by number, and — sent from still-swift-363 |
Record-literal instantiation: candidates and routes, with its own diagnostic
When a record literal names a constructor, the check must select the field
template to instantiate. Where that selection is not available, the previous
behaviour was to pick something anyway. This models the selection explicitly
and refuses when it is not determined.
The design centre is candidates-and-routes, not a canonical Node
Returning one canonical
Nodefor the expected type would rebuild the very bugthis repairs: it makes an unforced choice at the point where the ambiguity
lives, and then every consumer inherits that choice as if it were a fact. So
the expected type is read as a set of candidate constructor domains, each
tagged with the
ExpectedTypeRoutethat reached it:WholeExpectedTypeCardinalityOptionalWrapperNominalOptionalWrapperCollectionElementAliasTargetCandidates are deduped by owner identity, not by spelling. Selection then
folds over the domain and has exactly three outcomes — 0 owners, 1 owner, many
owners — and only the 1-owner case instantiates. Many owners refuses and
names every owner; selecting one by route order would be the absorbing
fallback (DESIGN §5), which is the failure this PR exists to close.
Why it has its own diagnostic
The decline is reported as
RecordLitInstantiationUndetermined { declared, cause, span }rather than by borrowing an existing variant. #10187's bodyargues the general form of this — ONE VARIANT MAY NOT ANSWER FOR TWO CAUSES —
and the rule applies to this PR's own reporting first.
The message says explicitly that it counts the check's own deficit, not a
defect in the code at that position, so the count cannot be read as an
accusation against the corpus. The cause is carried structurally as
RecordLitUnavailableCause, whoseAmbiguousVariantOwners { owners }arm iswhat makes the many-owner refusal name its owners rather than describe them.
Rebuilt on main
This branch was originally cut from
session/still-swift-363-first-conformanceand therefore carried 54 of that PR's files, which made it unreviewable and
unlandable independently. It has been reconstructed from
mainandforce-pushed.
c85792a045950d5ae0ad59b25837ad9f10b70ed0(tagchild-pre-rebuild)variant; that is discharged by construction above, not by sequencing. This PR
no longer depends on first()/last(): construct the declared Optional, repair the corpus that consumes it, and withdraw the decline candidate #10187 in either direction.
Evidence
ct_record_lit_domain_selection_tests— the routes each produce a domain, and dedup is by owner identity.ct_instantiation_unavailable_refuses_fallback_test— a constructor reachable by two routes refuses and names every owner. Its assertion states what a0and a2would each mean, so a silent route regression reds rather than passing.🤖 Generated with Claude Code
https://claude.ai/code/session_01HsALPpj3hERxcuCfK6Cc23