Skip to content

flaky: capture-bearing class factory reports .name === undefined on some builds (build-nondeterministic) #6482

Description

@proggeramlug

Summary

#6470 (be2e23f86, "per-evaluation captures for class declarations in function bodies") regressed class .name for a captured-param class-declaration factory. A named class declared inside a factory function that captures an outer parameter now reports .name === undefined instead of its declared name.

Repro

function makeTagged(tag: string) {
  class Inner {
    readonly _tag = tag;          // captures the outer `tag` param
    who() { return "tagged:" + this._tag; }
  }
  return Inner;
}
const T = makeTagged("S");
console.log(JSON.stringify(T.name));  // node: "Inner"   perry(main): undefined
console.log(new T().who());           // node: "tagged:S"  perry: "tagged:S"  (construction is fine)

Construction, the captured field, and method dispatch all work — only .name is lost. Covered by the existing gap test test_gap_5952_mixin_factory_binding (case 7), which now fails on main.

Bisect

Mechanism

For a capturing class declaration with no static state, #6470 sets fresh_binding = true and binds the name to a ClassExprFresh per-evaluation object (lower_decl/body_stmt.rs). The fresh object gets the right class_id (so methods/construction work), but its class_id is never entered into the CLASS_NAMES registry: name registration (codegen/string_pool.rsjs_register_class_name) only fires for class_ids collected into named_classes, and this fresh-factory template ends up excluded (classified anon / name-mismatched). .name then resolves via class_name_for_id(class_id)Noneundefined. Named class expressions through the same ClassExprFresh machinery keep their name, so the gap is specific to the declaration route + the specialize_captured_class_factories interaction.

Impact

Blocks conformance-smoke (shard containing test_gap_5952) on every PR branched off current main — surfaced while merging #6476 (unrelated streams PR). Mixin/class-factory patterns that read .name (incl. effect-style tagged classes) are affected.

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Type

    No type

    Fields

    No fields configured for issues without a type.

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions