Skip to content

Commit 0477f91

Browse files
Merge pull request microsoft#20928 from Microsoft/initializerWithPropertyAccessUseBeforeDeclaration
Check whether we have a class before testing whether we have a super-class
2 parents 679bfd4 + b899c49 commit 0477f91

6 files changed

Lines changed: 190 additions & 0 deletions

src/compiler/checker.ts

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -15873,6 +15873,9 @@ namespace ts {
1587315873
* In that case we won't consider it used before its declaration, because it gets its value from the superclass' declaration.
1587415874
*/
1587515875
function isPropertyDeclaredInAncestorClass(prop: Symbol): boolean {
15876+
if (!(prop.parent.flags & SymbolFlags.Class)) {
15877+
return false;
15878+
}
1587615879
let classType = getTypeOfSymbol(prop.parent) as InterfaceType;
1587715880
while (true) {
1587815881
classType = getSuperClass(classType);
Lines changed: 36 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,36 @@
1+
tests/cases/compiler/classStaticInitializersUsePropertiesBeforeDeclaration.ts(2,25): error TS2450: Enum 'Enum' used before its declaration.
2+
tests/cases/compiler/classStaticInitializersUsePropertiesBeforeDeclaration.ts(2,30): error TS2448: Block-scoped variable 'A' used before its declaration.
3+
tests/cases/compiler/classStaticInitializersUsePropertiesBeforeDeclaration.ts(3,31): error TS2448: Block-scoped variable 'ObjLiteral' used before its declaration.
4+
tests/cases/compiler/classStaticInitializersUsePropertiesBeforeDeclaration.ts(3,42): error TS2448: Block-scoped variable 'A' used before its declaration.
5+
tests/cases/compiler/classStaticInitializersUsePropertiesBeforeDeclaration.ts(4,40): error TS2448: Block-scoped variable 'A' used before its declaration.
6+
7+
8+
==== tests/cases/compiler/classStaticInitializersUsePropertiesBeforeDeclaration.ts (5 errors) ====
9+
class Foo {
10+
static enumMember = Enum.A;
11+
~~~~
12+
!!! error TS2450: Enum 'Enum' used before its declaration.
13+
~
14+
!!! error TS2448: Block-scoped variable 'A' used before its declaration.
15+
static objLiteralMember = ObjLiteral.A;
16+
~~~~~~~~~~
17+
!!! error TS2448: Block-scoped variable 'ObjLiteral' used before its declaration.
18+
~
19+
!!! error TS2448: Block-scoped variable 'A' used before its declaration.
20+
static namespaceMember = Namespace.A;
21+
~
22+
!!! error TS2448: Block-scoped variable 'A' used before its declaration.
23+
}
24+
25+
enum Enum {
26+
A
27+
}
28+
29+
const ObjLiteral = {
30+
A: 0
31+
};
32+
33+
namespace Namespace {
34+
export let A = 0
35+
}
36+
Lines changed: 40 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,40 @@
1+
//// [classStaticInitializersUsePropertiesBeforeDeclaration.ts]
2+
class Foo {
3+
static enumMember = Enum.A;
4+
static objLiteralMember = ObjLiteral.A;
5+
static namespaceMember = Namespace.A;
6+
}
7+
8+
enum Enum {
9+
A
10+
}
11+
12+
const ObjLiteral = {
13+
A: 0
14+
};
15+
16+
namespace Namespace {
17+
export let A = 0
18+
}
19+
20+
21+
//// [classStaticInitializersUsePropertiesBeforeDeclaration.js]
22+
var Foo = /** @class */ (function () {
23+
function Foo() {
24+
}
25+
Foo.enumMember = Enum.A;
26+
Foo.objLiteralMember = ObjLiteral.A;
27+
Foo.namespaceMember = Namespace.A;
28+
return Foo;
29+
}());
30+
var Enum;
31+
(function (Enum) {
32+
Enum[Enum["A"] = 0] = "A";
33+
})(Enum || (Enum = {}));
34+
var ObjLiteral = {
35+
A: 0
36+
};
37+
var Namespace;
38+
(function (Namespace) {
39+
Namespace.A = 0;
40+
})(Namespace || (Namespace = {}));
Lines changed: 45 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,45 @@
1+
=== tests/cases/compiler/classStaticInitializersUsePropertiesBeforeDeclaration.ts ===
2+
class Foo {
3+
>Foo : Symbol(Foo, Decl(classStaticInitializersUsePropertiesBeforeDeclaration.ts, 0, 0))
4+
5+
static enumMember = Enum.A;
6+
>enumMember : Symbol(Foo.enumMember, Decl(classStaticInitializersUsePropertiesBeforeDeclaration.ts, 0, 11))
7+
>Enum.A : Symbol(Enum.A, Decl(classStaticInitializersUsePropertiesBeforeDeclaration.ts, 6, 11))
8+
>Enum : Symbol(Enum, Decl(classStaticInitializersUsePropertiesBeforeDeclaration.ts, 4, 1))
9+
>A : Symbol(Enum.A, Decl(classStaticInitializersUsePropertiesBeforeDeclaration.ts, 6, 11))
10+
11+
static objLiteralMember = ObjLiteral.A;
12+
>objLiteralMember : Symbol(Foo.objLiteralMember, Decl(classStaticInitializersUsePropertiesBeforeDeclaration.ts, 1, 31))
13+
>ObjLiteral.A : Symbol(A, Decl(classStaticInitializersUsePropertiesBeforeDeclaration.ts, 10, 20))
14+
>ObjLiteral : Symbol(ObjLiteral, Decl(classStaticInitializersUsePropertiesBeforeDeclaration.ts, 10, 5))
15+
>A : Symbol(A, Decl(classStaticInitializersUsePropertiesBeforeDeclaration.ts, 10, 20))
16+
17+
static namespaceMember = Namespace.A;
18+
>namespaceMember : Symbol(Foo.namespaceMember, Decl(classStaticInitializersUsePropertiesBeforeDeclaration.ts, 2, 43))
19+
>Namespace.A : Symbol(Namespace.A, Decl(classStaticInitializersUsePropertiesBeforeDeclaration.ts, 15, 14))
20+
>Namespace : Symbol(Namespace, Decl(classStaticInitializersUsePropertiesBeforeDeclaration.ts, 12, 2))
21+
>A : Symbol(Namespace.A, Decl(classStaticInitializersUsePropertiesBeforeDeclaration.ts, 15, 14))
22+
}
23+
24+
enum Enum {
25+
>Enum : Symbol(Enum, Decl(classStaticInitializersUsePropertiesBeforeDeclaration.ts, 4, 1))
26+
27+
A
28+
>A : Symbol(Enum.A, Decl(classStaticInitializersUsePropertiesBeforeDeclaration.ts, 6, 11))
29+
}
30+
31+
const ObjLiteral = {
32+
>ObjLiteral : Symbol(ObjLiteral, Decl(classStaticInitializersUsePropertiesBeforeDeclaration.ts, 10, 5))
33+
34+
A: 0
35+
>A : Symbol(A, Decl(classStaticInitializersUsePropertiesBeforeDeclaration.ts, 10, 20))
36+
37+
};
38+
39+
namespace Namespace {
40+
>Namespace : Symbol(Namespace, Decl(classStaticInitializersUsePropertiesBeforeDeclaration.ts, 12, 2))
41+
42+
export let A = 0
43+
>A : Symbol(A, Decl(classStaticInitializersUsePropertiesBeforeDeclaration.ts, 15, 14))
44+
}
45+
Lines changed: 48 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,48 @@
1+
=== tests/cases/compiler/classStaticInitializersUsePropertiesBeforeDeclaration.ts ===
2+
class Foo {
3+
>Foo : Foo
4+
5+
static enumMember = Enum.A;
6+
>enumMember : Enum
7+
>Enum.A : Enum
8+
>Enum : typeof Enum
9+
>A : Enum
10+
11+
static objLiteralMember = ObjLiteral.A;
12+
>objLiteralMember : number
13+
>ObjLiteral.A : number
14+
>ObjLiteral : { A: number; }
15+
>A : number
16+
17+
static namespaceMember = Namespace.A;
18+
>namespaceMember : number
19+
>Namespace.A : number
20+
>Namespace : typeof Namespace
21+
>A : number
22+
}
23+
24+
enum Enum {
25+
>Enum : Enum
26+
27+
A
28+
>A : Enum
29+
}
30+
31+
const ObjLiteral = {
32+
>ObjLiteral : { A: number; }
33+
>{ A: 0} : { A: number; }
34+
35+
A: 0
36+
>A : number
37+
>0 : 0
38+
39+
};
40+
41+
namespace Namespace {
42+
>Namespace : typeof Namespace
43+
44+
export let A = 0
45+
>A : number
46+
>0 : 0
47+
}
48+
Lines changed: 18 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,18 @@
1+
2+
class Foo {
3+
static enumMember = Enum.A;
4+
static objLiteralMember = ObjLiteral.A;
5+
static namespaceMember = Namespace.A;
6+
}
7+
8+
enum Enum {
9+
A
10+
}
11+
12+
const ObjLiteral = {
13+
A: 0
14+
};
15+
16+
namespace Namespace {
17+
export let A = 0
18+
}

0 commit comments

Comments
 (0)