Skip to content

A capture-free class expression evaluated twice returns the same constructor #11298

Description

@proggeramlug

Evaluating a class expression that captures nothing twice returns the same constructor. A property defined on the second evaluation's prototype is therefore visible to instances of the first.

function makeClass() { return class { constructor() {} }; }
const K1 = makeClass(), K2 = makeClass(); let seen = -1;
Object.defineProperty(K2.prototype, "k", { set(v: number) { seen = v; }, configurable: true });
const o: any = new K1(); o.k = 4;
console.log(seen, Object.prototype.hasOwnProperty.call(o, "k"), K1 === K2, Object.getPrototypeOf(o) === K2.prototype);
runtime output
node -1 true false false
perry main 4 false true true

Every evaluation of a class expression must produce a distinct constructor and a distinct prototype (ClassDefinitionEvaluation). The capture-free case lowers to one shared template class. PR #11297 makes classes that capture something distinct per evaluation, but it does not cover this case: a class with no captures never enters that path.

Found by the inherited-access lane while testing prototype-in-shape.

Activity

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Type

    No type

    Projects

    No projects

      Milestone

      No milestone

      Relationships

      None yet

      Development

      No branches or pull requests

      Issue actions