mirror of
https://github.com/microsoft/TypeScript.git
synced 2026-02-15 11:35:42 -06:00
Fix 8467: Fix incorrect emit for accessing static property in static propertyDeclaration (#8551)
* Fix incorrect emit for accessing static property in static propertyDeclaration * Update tests and baselines * Update function name * Fix when accessing static property inside arrow function * Add tests and baselines
This commit is contained in:
parent
e182ecf2c9
commit
be2ca35b00
@ -1673,6 +1673,21 @@ var __awaiter = (this && this.__awaiter) || function (thisArg, _arguments, P, ge
|
||||
return false;
|
||||
}
|
||||
|
||||
function getClassExpressionInPropertyAccessInStaticPropertyDeclaration(node: Identifier) {
|
||||
if (languageVersion >= ScriptTarget.ES6) {
|
||||
let parent = node.parent;
|
||||
if (parent.kind === SyntaxKind.PropertyAccessExpression && (<PropertyAccessExpression>parent).expression === node) {
|
||||
parent = parent.parent;
|
||||
while (parent && parent.kind !== SyntaxKind.PropertyDeclaration) {
|
||||
parent = parent.parent;
|
||||
}
|
||||
return parent && parent.kind === SyntaxKind.PropertyDeclaration && (parent.flags & NodeFlags.Static) !== 0 &&
|
||||
parent.parent.kind === SyntaxKind.ClassExpression ? parent.parent : undefined;
|
||||
}
|
||||
}
|
||||
return undefined;
|
||||
}
|
||||
|
||||
function emitIdentifier(node: Identifier) {
|
||||
if (convertedLoopState) {
|
||||
if (node.text == "arguments" && resolver.isArgumentsLocalBinding(node)) {
|
||||
@ -1687,6 +1702,14 @@ var __awaiter = (this && this.__awaiter) || function (thisArg, _arguments, P, ge
|
||||
write(node.text);
|
||||
}
|
||||
else if (isExpressionIdentifier(node)) {
|
||||
const classExpression = getClassExpressionInPropertyAccessInStaticPropertyDeclaration(node);
|
||||
if (classExpression) {
|
||||
const declaration = resolver.getReferencedValueDeclaration(node);
|
||||
if (declaration === classExpression) {
|
||||
write(getGeneratedNameForNode(declaration.name));
|
||||
return;
|
||||
}
|
||||
}
|
||||
emitExpressionIdentifier(node);
|
||||
}
|
||||
else if (isNameOfNestedBlockScopedRedeclarationOrCapturedBinding(node)) {
|
||||
@ -5086,13 +5109,13 @@ const _super = (function (geti, seti) {
|
||||
}
|
||||
}
|
||||
|
||||
function emitPropertyDeclaration(node: ClassLikeDeclaration, property: PropertyDeclaration, receiver?: Identifier, isExpression?: boolean) {
|
||||
function emitPropertyDeclaration(node: ClassLikeDeclaration, property: PropertyDeclaration, receiver?: string, isExpression?: boolean) {
|
||||
writeLine();
|
||||
emitLeadingComments(property);
|
||||
emitStart(property);
|
||||
emitStart(property.name);
|
||||
if (receiver) {
|
||||
emit(receiver);
|
||||
write(receiver);
|
||||
}
|
||||
else {
|
||||
if (property.flags & NodeFlags.Static) {
|
||||
@ -5511,13 +5534,16 @@ const _super = (function (geti, seti) {
|
||||
// of it have been initialized by the time it is used.
|
||||
const staticProperties = getInitializedProperties(node, /*isStatic*/ true);
|
||||
const isClassExpressionWithStaticProperties = staticProperties.length > 0 && node.kind === SyntaxKind.ClassExpression;
|
||||
let tempVariable: Identifier;
|
||||
let generatedName: string;
|
||||
|
||||
if (isClassExpressionWithStaticProperties) {
|
||||
tempVariable = createAndRecordTempVariable(TempFlags.Auto);
|
||||
generatedName = getGeneratedNameForNode(node.name);
|
||||
const synthesizedNode = <Identifier>createSynthesizedNode(SyntaxKind.Identifier);
|
||||
synthesizedNode.text = generatedName;
|
||||
recordTempDeclaration(synthesizedNode);
|
||||
write("(");
|
||||
increaseIndent();
|
||||
emit(tempVariable);
|
||||
emit(synthesizedNode);
|
||||
write(" = ");
|
||||
}
|
||||
|
||||
@ -5571,11 +5597,11 @@ const _super = (function (geti, seti) {
|
||||
for (const property of staticProperties) {
|
||||
write(",");
|
||||
writeLine();
|
||||
emitPropertyDeclaration(node, property, /*receiver*/ tempVariable, /*isExpression*/ true);
|
||||
emitPropertyDeclaration(node, property, /*receiver*/ generatedName, /*isExpression*/ true);
|
||||
}
|
||||
write(",");
|
||||
writeLine();
|
||||
emit(tempVariable);
|
||||
write(generatedName);
|
||||
decreaseIndent();
|
||||
write(")");
|
||||
}
|
||||
|
||||
@ -1,10 +1,15 @@
|
||||
//// [classExpressionWithStaticPropertiesES61.ts]
|
||||
var v = class C { static a = 1; static b = 2 };
|
||||
var v = class C {
|
||||
static a = 1;
|
||||
static b = 2;
|
||||
static c = C.a + 3;
|
||||
};
|
||||
|
||||
//// [classExpressionWithStaticPropertiesES61.js]
|
||||
var v = (_a = class C {
|
||||
var v = (C_1 = class C {
|
||||
},
|
||||
_a.a = 1,
|
||||
_a.b = 2,
|
||||
_a);
|
||||
var _a;
|
||||
C_1.a = 1,
|
||||
C_1.b = 2,
|
||||
C_1.c = C_1.a + 3,
|
||||
C_1);
|
||||
var C_1;
|
||||
|
||||
@ -1,7 +1,18 @@
|
||||
=== tests/cases/compiler/classExpressionWithStaticPropertiesES61.ts ===
|
||||
var v = class C { static a = 1; static b = 2 };
|
||||
var v = class C {
|
||||
>v : Symbol(v, Decl(classExpressionWithStaticPropertiesES61.ts, 0, 3))
|
||||
>C : Symbol(C, Decl(classExpressionWithStaticPropertiesES61.ts, 0, 7))
|
||||
>a : Symbol(C.a, Decl(classExpressionWithStaticPropertiesES61.ts, 0, 17))
|
||||
>b : Symbol(C.b, Decl(classExpressionWithStaticPropertiesES61.ts, 0, 31))
|
||||
|
||||
static a = 1;
|
||||
>a : Symbol(C.a, Decl(classExpressionWithStaticPropertiesES61.ts, 0, 17))
|
||||
|
||||
static b = 2;
|
||||
>b : Symbol(C.b, Decl(classExpressionWithStaticPropertiesES61.ts, 1, 17))
|
||||
|
||||
static c = C.a + 3;
|
||||
>c : Symbol(C.c, Decl(classExpressionWithStaticPropertiesES61.ts, 2, 17))
|
||||
>C.a : Symbol(C.a, Decl(classExpressionWithStaticPropertiesES61.ts, 0, 17))
|
||||
>C : Symbol(C, Decl(classExpressionWithStaticPropertiesES61.ts, 0, 7))
|
||||
>a : Symbol(C.a, Decl(classExpressionWithStaticPropertiesES61.ts, 0, 17))
|
||||
|
||||
};
|
||||
|
||||
@ -1,10 +1,23 @@
|
||||
=== tests/cases/compiler/classExpressionWithStaticPropertiesES61.ts ===
|
||||
var v = class C { static a = 1; static b = 2 };
|
||||
var v = class C {
|
||||
>v : typeof C
|
||||
>class C { static a = 1; static b = 2 } : typeof C
|
||||
>class C { static a = 1; static b = 2; static c = C.a + 3;} : typeof C
|
||||
>C : typeof C
|
||||
|
||||
static a = 1;
|
||||
>a : number
|
||||
>1 : number
|
||||
|
||||
static b = 2;
|
||||
>b : number
|
||||
>2 : number
|
||||
|
||||
static c = C.a + 3;
|
||||
>c : number
|
||||
>C.a + 3 : number
|
||||
>C.a : number
|
||||
>C : typeof C
|
||||
>a : number
|
||||
>3 : number
|
||||
|
||||
};
|
||||
|
||||
@ -1,9 +1,20 @@
|
||||
//// [classExpressionWithStaticPropertiesES62.ts]
|
||||
var v = class C { static a = 1; static b };
|
||||
var v = class C {
|
||||
static a = 1;
|
||||
static b
|
||||
static c = {
|
||||
x: "hi"
|
||||
}
|
||||
static d = C.c.x + " world";
|
||||
};
|
||||
|
||||
//// [classExpressionWithStaticPropertiesES62.js]
|
||||
var v = (_a = class C {
|
||||
var v = (C_1 = class C {
|
||||
},
|
||||
_a.a = 1,
|
||||
_a);
|
||||
var _a;
|
||||
C_1.a = 1,
|
||||
C_1.c = {
|
||||
x: "hi"
|
||||
},
|
||||
C_1.d = C_1.c.x + " world",
|
||||
C_1);
|
||||
var C_1;
|
||||
|
||||
@ -1,7 +1,26 @@
|
||||
=== tests/cases/compiler/classExpressionWithStaticPropertiesES62.ts ===
|
||||
var v = class C { static a = 1; static b };
|
||||
var v = class C {
|
||||
>v : Symbol(v, Decl(classExpressionWithStaticPropertiesES62.ts, 0, 3))
|
||||
>C : Symbol(C, Decl(classExpressionWithStaticPropertiesES62.ts, 0, 7))
|
||||
>a : Symbol(C.a, Decl(classExpressionWithStaticPropertiesES62.ts, 0, 17))
|
||||
>b : Symbol(C.b, Decl(classExpressionWithStaticPropertiesES62.ts, 0, 31))
|
||||
|
||||
static a = 1;
|
||||
>a : Symbol(C.a, Decl(classExpressionWithStaticPropertiesES62.ts, 0, 17))
|
||||
|
||||
static b
|
||||
>b : Symbol(C.b, Decl(classExpressionWithStaticPropertiesES62.ts, 1, 17))
|
||||
|
||||
static c = {
|
||||
>c : Symbol(C.c, Decl(classExpressionWithStaticPropertiesES62.ts, 2, 12))
|
||||
|
||||
x: "hi"
|
||||
>x : Symbol(x, Decl(classExpressionWithStaticPropertiesES62.ts, 3, 16))
|
||||
}
|
||||
static d = C.c.x + " world";
|
||||
>d : Symbol(C.d, Decl(classExpressionWithStaticPropertiesES62.ts, 5, 5))
|
||||
>C.c.x : Symbol(x, Decl(classExpressionWithStaticPropertiesES62.ts, 3, 16))
|
||||
>C.c : Symbol(C.c, Decl(classExpressionWithStaticPropertiesES62.ts, 2, 12))
|
||||
>C : Symbol(C, Decl(classExpressionWithStaticPropertiesES62.ts, 0, 7))
|
||||
>c : Symbol(C.c, Decl(classExpressionWithStaticPropertiesES62.ts, 2, 12))
|
||||
>x : Symbol(x, Decl(classExpressionWithStaticPropertiesES62.ts, 3, 16))
|
||||
|
||||
};
|
||||
|
||||
@ -1,9 +1,32 @@
|
||||
=== tests/cases/compiler/classExpressionWithStaticPropertiesES62.ts ===
|
||||
var v = class C { static a = 1; static b };
|
||||
var v = class C {
|
||||
>v : typeof C
|
||||
>class C { static a = 1; static b } : typeof C
|
||||
>class C { static a = 1; static b static c = { x: "hi" } static d = C.c.x + " world"; } : typeof C
|
||||
>C : typeof C
|
||||
|
||||
static a = 1;
|
||||
>a : number
|
||||
>1 : number
|
||||
|
||||
static b
|
||||
>b : any
|
||||
|
||||
static c = {
|
||||
>c : { x: string; }
|
||||
>{ x: "hi" } : { x: string; }
|
||||
|
||||
x: "hi"
|
||||
>x : string
|
||||
>"hi" : string
|
||||
}
|
||||
static d = C.c.x + " world";
|
||||
>d : string
|
||||
>C.c.x + " world" : string
|
||||
>C.c.x : string
|
||||
>C.c : { x: string; }
|
||||
>C : typeof C
|
||||
>c : { x: string; }
|
||||
>x : string
|
||||
>" world" : string
|
||||
|
||||
};
|
||||
|
||||
@ -0,0 +1,23 @@
|
||||
//// [classExpressionWithStaticPropertiesES63.ts]
|
||||
|
||||
declare var console: any;
|
||||
const arr: {y(): number}[] = [];
|
||||
for (let i = 0; i < 3; i++) {
|
||||
arr.push(class C {
|
||||
static x = i;
|
||||
static y = () => C.x * 2;
|
||||
});
|
||||
}
|
||||
arr.forEach(C => console.log(C.y()));
|
||||
|
||||
//// [classExpressionWithStaticPropertiesES63.js]
|
||||
const arr = [];
|
||||
for (let i = 0; i < 3; i++) {
|
||||
arr.push((C_1 = class C {
|
||||
},
|
||||
C_1.x = i,
|
||||
C_1.y = () => C_1.x * 2,
|
||||
C_1));
|
||||
}
|
||||
arr.forEach(C => console.log(C.y()));
|
||||
var C_1;
|
||||
@ -0,0 +1,42 @@
|
||||
=== tests/cases/compiler/classExpressionWithStaticPropertiesES63.ts ===
|
||||
|
||||
declare var console: any;
|
||||
>console : Symbol(console, Decl(classExpressionWithStaticPropertiesES63.ts, 1, 11))
|
||||
|
||||
const arr: {y(): number}[] = [];
|
||||
>arr : Symbol(arr, Decl(classExpressionWithStaticPropertiesES63.ts, 2, 5))
|
||||
>y : Symbol(y, Decl(classExpressionWithStaticPropertiesES63.ts, 2, 12))
|
||||
|
||||
for (let i = 0; i < 3; i++) {
|
||||
>i : Symbol(i, Decl(classExpressionWithStaticPropertiesES63.ts, 3, 8))
|
||||
>i : Symbol(i, Decl(classExpressionWithStaticPropertiesES63.ts, 3, 8))
|
||||
>i : Symbol(i, Decl(classExpressionWithStaticPropertiesES63.ts, 3, 8))
|
||||
|
||||
arr.push(class C {
|
||||
>arr.push : Symbol(Array.push, Decl(lib.es5.d.ts, --, --))
|
||||
>arr : Symbol(arr, Decl(classExpressionWithStaticPropertiesES63.ts, 2, 5))
|
||||
>push : Symbol(Array.push, Decl(lib.es5.d.ts, --, --))
|
||||
>C : Symbol(C, Decl(classExpressionWithStaticPropertiesES63.ts, 4, 13))
|
||||
|
||||
static x = i;
|
||||
>x : Symbol(C.x, Decl(classExpressionWithStaticPropertiesES63.ts, 4, 22))
|
||||
>i : Symbol(i, Decl(classExpressionWithStaticPropertiesES63.ts, 3, 8))
|
||||
|
||||
static y = () => C.x * 2;
|
||||
>y : Symbol(C.y, Decl(classExpressionWithStaticPropertiesES63.ts, 5, 21))
|
||||
>C.x : Symbol(C.x, Decl(classExpressionWithStaticPropertiesES63.ts, 4, 22))
|
||||
>C : Symbol(C, Decl(classExpressionWithStaticPropertiesES63.ts, 4, 13))
|
||||
>x : Symbol(C.x, Decl(classExpressionWithStaticPropertiesES63.ts, 4, 22))
|
||||
|
||||
});
|
||||
}
|
||||
arr.forEach(C => console.log(C.y()));
|
||||
>arr.forEach : Symbol(Array.forEach, Decl(lib.es5.d.ts, --, --))
|
||||
>arr : Symbol(arr, Decl(classExpressionWithStaticPropertiesES63.ts, 2, 5))
|
||||
>forEach : Symbol(Array.forEach, Decl(lib.es5.d.ts, --, --))
|
||||
>C : Symbol(C, Decl(classExpressionWithStaticPropertiesES63.ts, 9, 12))
|
||||
>console : Symbol(console, Decl(classExpressionWithStaticPropertiesES63.ts, 1, 11))
|
||||
>C.y : Symbol(y, Decl(classExpressionWithStaticPropertiesES63.ts, 2, 12))
|
||||
>C : Symbol(C, Decl(classExpressionWithStaticPropertiesES63.ts, 9, 12))
|
||||
>y : Symbol(y, Decl(classExpressionWithStaticPropertiesES63.ts, 2, 12))
|
||||
|
||||
@ -0,0 +1,58 @@
|
||||
=== tests/cases/compiler/classExpressionWithStaticPropertiesES63.ts ===
|
||||
|
||||
declare var console: any;
|
||||
>console : any
|
||||
|
||||
const arr: {y(): number}[] = [];
|
||||
>arr : { y(): number; }[]
|
||||
>y : () => number
|
||||
>[] : undefined[]
|
||||
|
||||
for (let i = 0; i < 3; i++) {
|
||||
>i : number
|
||||
>0 : number
|
||||
>i < 3 : boolean
|
||||
>i : number
|
||||
>3 : number
|
||||
>i++ : number
|
||||
>i : number
|
||||
|
||||
arr.push(class C {
|
||||
>arr.push(class C { static x = i; static y = () => C.x * 2; }) : number
|
||||
>arr.push : (...items: { y(): number; }[]) => number
|
||||
>arr : { y(): number; }[]
|
||||
>push : (...items: { y(): number; }[]) => number
|
||||
>class C { static x = i; static y = () => C.x * 2; } : typeof C
|
||||
>C : typeof C
|
||||
|
||||
static x = i;
|
||||
>x : number
|
||||
>i : number
|
||||
|
||||
static y = () => C.x * 2;
|
||||
>y : () => number
|
||||
>() => C.x * 2 : () => number
|
||||
>C.x * 2 : number
|
||||
>C.x : number
|
||||
>C : typeof C
|
||||
>x : number
|
||||
>2 : number
|
||||
|
||||
});
|
||||
}
|
||||
arr.forEach(C => console.log(C.y()));
|
||||
>arr.forEach(C => console.log(C.y())) : void
|
||||
>arr.forEach : (callbackfn: (value: { y(): number; }, index: number, array: { y(): number; }[]) => void, thisArg?: any) => void
|
||||
>arr : { y(): number; }[]
|
||||
>forEach : (callbackfn: (value: { y(): number; }, index: number, array: { y(): number; }[]) => void, thisArg?: any) => void
|
||||
>C => console.log(C.y()) : (C: { y(): number; }) => any
|
||||
>C : { y(): number; }
|
||||
>console.log(C.y()) : any
|
||||
>console.log : any
|
||||
>console : any
|
||||
>log : any
|
||||
>C.y() : number
|
||||
>C.y : () => number
|
||||
>C : { y(): number; }
|
||||
>y : () => number
|
||||
|
||||
@ -1,2 +1,6 @@
|
||||
//@target: es6
|
||||
var v = class C { static a = 1; static b = 2 };
|
||||
var v = class C {
|
||||
static a = 1;
|
||||
static b = 2;
|
||||
static c = C.a + 3;
|
||||
};
|
||||
@ -1,2 +1,9 @@
|
||||
//@target: es6
|
||||
var v = class C { static a = 1; static b };
|
||||
var v = class C {
|
||||
static a = 1;
|
||||
static b
|
||||
static c = {
|
||||
x: "hi"
|
||||
}
|
||||
static d = C.c.x + " world";
|
||||
};
|
||||
@ -0,0 +1,11 @@
|
||||
//@target: es6
|
||||
|
||||
declare var console: any;
|
||||
const arr: {y(): number}[] = [];
|
||||
for (let i = 0; i < 3; i++) {
|
||||
arr.push(class C {
|
||||
static x = i;
|
||||
static y = () => C.x * 2;
|
||||
});
|
||||
}
|
||||
arr.forEach(C => console.log(C.y()));
|
||||
Loading…
x
Reference in New Issue
Block a user