Skip to content

Commit

Permalink
Error on override used on dynamically named class members (#60691)
Browse files Browse the repository at this point in the history
  • Loading branch information
Andarist authored Dec 6, 2024
1 parent edd278a commit 239a2a9
Show file tree
Hide file tree
Showing 29 changed files with 1,358 additions and 0 deletions.
9 changes: 9 additions & 0 deletions src/compiler/checker.ts
Original file line number Diff line number Diff line change
Expand Up @@ -46774,6 +46774,15 @@ export function createTypeChecker(host: TypeCheckerHost): TypeChecker {
): MemberOverrideStatus {
const isJs = isInJSFile(node);
const nodeInAmbientContext = !!(node.flags & NodeFlags.Ambient);
if (memberHasOverrideModifier && member?.valueDeclaration && isClassElement(member.valueDeclaration) && member.valueDeclaration.name && isNonBindableDynamicName(member.valueDeclaration.name)) {
error(
errorNode,
isJs ?
Diagnostics.This_member_cannot_have_a_JSDoc_comment_with_an_override_tag_because_its_name_is_dynamic :
Diagnostics.This_member_cannot_have_an_override_modifier_because_its_name_is_dynamic,
);
return MemberOverrideStatus.HasInvalidOverride;
}
if (baseWithThis && (memberHasOverrideModifier || compilerOptions.noImplicitOverride)) {
const thisType = memberIsStatic ? staticType : typeWithThis;
const baseType = memberIsStatic ? baseStaticType : baseWithThis;
Expand Down
8 changes: 8 additions & 0 deletions src/compiler/diagnosticMessages.json
Original file line number Diff line number Diff line change
Expand Up @@ -4417,6 +4417,14 @@
"category": "Error",
"code": 4126
},
"This member cannot have an 'override' modifier because its name is dynamic.": {
"category": "Error",
"code": 4127
},
"This member cannot have a JSDoc comment with an '@override' tag because its name is dynamic.": {
"category": "Error",
"code": 4128
},

"The current host does not support the '{0}' option.": {
"category": "Error",
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,33 @@
overrideDynamicName1.ts(8,12): error TS4127: This member cannot have an 'override' modifier because its name is dynamic.
overrideDynamicName1.ts(22,12): error TS4127: This member cannot have an 'override' modifier because its name is dynamic.


==== overrideDynamicName1.ts (2 errors) ====
let prop = "foo"

class Base1 {
[prop]() {}
}

class Derived1 extends Base1 {
override [prop]() {}
~~~~~~
!!! error TS4127: This member cannot have an 'override' modifier because its name is dynamic.
}

class Base2 {
[prop]() {}
}

class Derived2 extends Base2 {
[prop]() {}
}

class Base3 {}

class Derived3 extends Base3 {
override [prop]() {}
~~~~~~
!!! error TS4127: This member cannot have an 'override' modifier because its name is dynamic.
}

Original file line number Diff line number Diff line change
@@ -0,0 +1,49 @@
//// [tests/cases/conformance/override/overrideDynamicName1.ts] ////

//// [overrideDynamicName1.ts]
let prop = "foo"

class Base1 {
[prop]() {}
}

class Derived1 extends Base1 {
override [prop]() {}
}

class Base2 {
[prop]() {}
}

class Derived2 extends Base2 {
[prop]() {}
}

class Base3 {}

class Derived3 extends Base3 {
override [prop]() {}
}




//// [overrideDynamicName1.d.ts]
declare let prop: string;
declare class Base1 {
[x: string]: () => void;
}
declare class Derived1 extends Base1 {
[x: string]: () => void;
}
declare class Base2 {
[x: string]: () => void;
}
declare class Derived2 extends Base2 {
[x: string]: () => void;
}
declare class Base3 {
}
declare class Derived3 extends Base3 {
[x: string]: () => void;
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,52 @@
//// [tests/cases/conformance/override/overrideDynamicName1.ts] ////

=== overrideDynamicName1.ts ===
let prop = "foo"
>prop : Symbol(prop, Decl(overrideDynamicName1.ts, 0, 3))

class Base1 {
>Base1 : Symbol(Base1, Decl(overrideDynamicName1.ts, 0, 16))

[prop]() {}
>[prop] : Symbol(Base1[prop], Decl(overrideDynamicName1.ts, 2, 13))
>prop : Symbol(prop, Decl(overrideDynamicName1.ts, 0, 3))
}

class Derived1 extends Base1 {
>Derived1 : Symbol(Derived1, Decl(overrideDynamicName1.ts, 4, 1))
>Base1 : Symbol(Base1, Decl(overrideDynamicName1.ts, 0, 16))

override [prop]() {}
>[prop] : Symbol(Derived1[prop], Decl(overrideDynamicName1.ts, 6, 30))
>prop : Symbol(prop, Decl(overrideDynamicName1.ts, 0, 3))
}

class Base2 {
>Base2 : Symbol(Base2, Decl(overrideDynamicName1.ts, 8, 1))

[prop]() {}
>[prop] : Symbol(Base2[prop], Decl(overrideDynamicName1.ts, 10, 13))
>prop : Symbol(prop, Decl(overrideDynamicName1.ts, 0, 3))
}

class Derived2 extends Base2 {
>Derived2 : Symbol(Derived2, Decl(overrideDynamicName1.ts, 12, 1))
>Base2 : Symbol(Base2, Decl(overrideDynamicName1.ts, 8, 1))

[prop]() {}
>[prop] : Symbol(Derived2[prop], Decl(overrideDynamicName1.ts, 14, 30))
>prop : Symbol(prop, Decl(overrideDynamicName1.ts, 0, 3))
}

class Base3 {}
>Base3 : Symbol(Base3, Decl(overrideDynamicName1.ts, 16, 1))

class Derived3 extends Base3 {
>Derived3 : Symbol(Derived3, Decl(overrideDynamicName1.ts, 18, 14))
>Base3 : Symbol(Base3, Decl(overrideDynamicName1.ts, 16, 1))

override [prop]() {}
>[prop] : Symbol(Derived3[prop], Decl(overrideDynamicName1.ts, 20, 30))
>prop : Symbol(prop, Decl(overrideDynamicName1.ts, 0, 3))
}

Original file line number Diff line number Diff line change
@@ -0,0 +1,74 @@
//// [tests/cases/conformance/override/overrideDynamicName1.ts] ////

=== overrideDynamicName1.ts ===
let prop = "foo"
>prop : string
> : ^^^^^^
>"foo" : "foo"
> : ^^^^^

class Base1 {
>Base1 : Base1
> : ^^^^^

[prop]() {}
>[prop] : () => void
> : ^^^^^^^^^^
>prop : string
> : ^^^^^^
}

class Derived1 extends Base1 {
>Derived1 : Derived1
> : ^^^^^^^^
>Base1 : Base1
> : ^^^^^

override [prop]() {}
>[prop] : () => void
> : ^^^^^^^^^^
>prop : string
> : ^^^^^^
}

class Base2 {
>Base2 : Base2
> : ^^^^^

[prop]() {}
>[prop] : () => void
> : ^^^^^^^^^^
>prop : string
> : ^^^^^^
}

class Derived2 extends Base2 {
>Derived2 : Derived2
> : ^^^^^^^^
>Base2 : Base2
> : ^^^^^

[prop]() {}
>[prop] : () => void
> : ^^^^^^^^^^
>prop : string
> : ^^^^^^
}

class Base3 {}
>Base3 : Base3
> : ^^^^^

class Derived3 extends Base3 {
>Derived3 : Derived3
> : ^^^^^^^^
>Base3 : Base3
> : ^^^^^

override [prop]() {}
>[prop] : () => void
> : ^^^^^^^^^^
>prop : string
> : ^^^^^^
}

Original file line number Diff line number Diff line change
@@ -0,0 +1,33 @@
overrideDynamicName1.ts(8,12): error TS4127: This member cannot have an 'override' modifier because its name is dynamic.
overrideDynamicName1.ts(22,12): error TS4127: This member cannot have an 'override' modifier because its name is dynamic.


==== overrideDynamicName1.ts (2 errors) ====
let prop = "foo"

class Base1 {
[prop]() {}
}

class Derived1 extends Base1 {
override [prop]() {}
~~~~~~
!!! error TS4127: This member cannot have an 'override' modifier because its name is dynamic.
}

class Base2 {
[prop]() {}
}

class Derived2 extends Base2 {
[prop]() {}
}

class Base3 {}

class Derived3 extends Base3 {
override [prop]() {}
~~~~~~
!!! error TS4127: This member cannot have an 'override' modifier because its name is dynamic.
}

Original file line number Diff line number Diff line change
@@ -0,0 +1,49 @@
//// [tests/cases/conformance/override/overrideDynamicName1.ts] ////

//// [overrideDynamicName1.ts]
let prop = "foo"

class Base1 {
[prop]() {}
}

class Derived1 extends Base1 {
override [prop]() {}
}

class Base2 {
[prop]() {}
}

class Derived2 extends Base2 {
[prop]() {}
}

class Base3 {}

class Derived3 extends Base3 {
override [prop]() {}
}




//// [overrideDynamicName1.d.ts]
declare let prop: string;
declare class Base1 {
[x: string]: () => void;
}
declare class Derived1 extends Base1 {
[x: string]: () => void;
}
declare class Base2 {
[x: string]: () => void;
}
declare class Derived2 extends Base2 {
[x: string]: () => void;
}
declare class Base3 {
}
declare class Derived3 extends Base3 {
[x: string]: () => void;
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,52 @@
//// [tests/cases/conformance/override/overrideDynamicName1.ts] ////

=== overrideDynamicName1.ts ===
let prop = "foo"
>prop : Symbol(prop, Decl(overrideDynamicName1.ts, 0, 3))

class Base1 {
>Base1 : Symbol(Base1, Decl(overrideDynamicName1.ts, 0, 16))

[prop]() {}
>[prop] : Symbol(Base1[prop], Decl(overrideDynamicName1.ts, 2, 13))
>prop : Symbol(prop, Decl(overrideDynamicName1.ts, 0, 3))
}

class Derived1 extends Base1 {
>Derived1 : Symbol(Derived1, Decl(overrideDynamicName1.ts, 4, 1))
>Base1 : Symbol(Base1, Decl(overrideDynamicName1.ts, 0, 16))

override [prop]() {}
>[prop] : Symbol(Derived1[prop], Decl(overrideDynamicName1.ts, 6, 30))
>prop : Symbol(prop, Decl(overrideDynamicName1.ts, 0, 3))
}

class Base2 {
>Base2 : Symbol(Base2, Decl(overrideDynamicName1.ts, 8, 1))

[prop]() {}
>[prop] : Symbol(Base2[prop], Decl(overrideDynamicName1.ts, 10, 13))
>prop : Symbol(prop, Decl(overrideDynamicName1.ts, 0, 3))
}

class Derived2 extends Base2 {
>Derived2 : Symbol(Derived2, Decl(overrideDynamicName1.ts, 12, 1))
>Base2 : Symbol(Base2, Decl(overrideDynamicName1.ts, 8, 1))

[prop]() {}
>[prop] : Symbol(Derived2[prop], Decl(overrideDynamicName1.ts, 14, 30))
>prop : Symbol(prop, Decl(overrideDynamicName1.ts, 0, 3))
}

class Base3 {}
>Base3 : Symbol(Base3, Decl(overrideDynamicName1.ts, 16, 1))

class Derived3 extends Base3 {
>Derived3 : Symbol(Derived3, Decl(overrideDynamicName1.ts, 18, 14))
>Base3 : Symbol(Base3, Decl(overrideDynamicName1.ts, 16, 1))

override [prop]() {}
>[prop] : Symbol(Derived3[prop], Decl(overrideDynamicName1.ts, 20, 30))
>prop : Symbol(prop, Decl(overrideDynamicName1.ts, 0, 3))
}

Loading

0 comments on commit 239a2a9

Please sign in to comment.