Skip to content

Commit b93da62

Browse files
authored
Emit non-identifier enum member references as typeof parent[some name] (microsoft#40679)
1 parent 798b18b commit b93da62

27 files changed

+143
-43
lines changed

src/compiler/checker.ts

Lines changed: 18 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -4403,13 +4403,26 @@ namespace ts {
44034403
if (type.flags & TypeFlags.EnumLiteral && !(type.flags & TypeFlags.Union)) {
44044404
const parentSymbol = getParentOfSymbol(type.symbol)!;
44054405
const parentName = symbolToTypeNode(parentSymbol, context, SymbolFlags.Type);
4406-
const enumLiteralName = getDeclaredTypeOfSymbol(parentSymbol) === type
4407-
? parentName
4408-
: appendReferenceToType(
4406+
if (getDeclaredTypeOfSymbol(parentSymbol) === type) {
4407+
return parentName;
4408+
}
4409+
const memberName = symbolName(type.symbol);
4410+
if (isIdentifierText(memberName, ScriptTarget.ES3)) {
4411+
return appendReferenceToType(
44094412
parentName as TypeReferenceNode | ImportTypeNode,
4410-
factory.createTypeReferenceNode(symbolName(type.symbol), /*typeArguments*/ undefined)
4413+
factory.createTypeReferenceNode(memberName, /*typeArguments*/ undefined)
44114414
);
4412-
return enumLiteralName;
4415+
}
4416+
if (isImportTypeNode(parentName)) {
4417+
(parentName as any).isTypeOf = true; // mutably update, node is freshly manufactured anyhow
4418+
return factory.createIndexedAccessTypeNode(parentName, factory.createLiteralTypeNode(factory.createStringLiteral(memberName)));
4419+
}
4420+
else if (isTypeReferenceNode(parentName)) {
4421+
return factory.createIndexedAccessTypeNode(factory.createTypeQueryNode(parentName.typeName), factory.createLiteralTypeNode(factory.createStringLiteral(memberName)));
4422+
}
4423+
else {
4424+
return Debug.fail("Unhandled type node kind returned from `symbolToTypeNode`.");
4425+
}
44134426
}
44144427
if (type.flags & TypeFlags.EnumLike) {
44154428
return symbolToTypeNode(type.symbol, context, SymbolFlags.Type);

tests/baselines/reference/ambientConstLiterals.types

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -12,7 +12,7 @@ enum E { A, B, C, "non identifier" }
1212
>A : E.A
1313
>B : E.B
1414
>C : E.C
15-
>"non identifier" : E.non identifier
15+
>"non identifier" : typeof E["non identifier"]
1616

1717
const c1 = "abc";
1818
>c1 : "abc"
@@ -54,8 +54,8 @@ const c8 = E.A;
5454
>A : E.A
5555

5656
const c8b = E["non identifier"];
57-
>c8b : E.non identifier
58-
>E["non identifier"] : E.non identifier
57+
>c8b : typeof E["non identifier"]
58+
>E["non identifier"] : typeof E["non identifier"]
5959
>E : typeof E
6060
>"non identifier" : "non identifier"
6161

tests/baselines/reference/bitwiseNotOperatorWithEnumType.types

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -5,7 +5,7 @@ enum ENUM1 { A, B, "" };
55
>ENUM1 : ENUM1
66
>A : ENUM1.A
77
>B : ENUM1.B
8-
>"" : ENUM1.
8+
>"" : typeof ENUM1[""]
99

1010
// enum type var
1111
var ResultIsNumber1 = ~ENUM1;

tests/baselines/reference/declFileEnums.types

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -83,7 +83,7 @@ enum e5 {
8383
>"Sunday" : e5.Sunday
8484

8585
"Weekend days"
86-
>"Weekend days" : e5.Weekend days
86+
>"Weekend days" : typeof e5["Weekend days"]
8787
}
8888

8989

Lines changed: 53 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,53 @@
1+
//// [declarationEmitSpreadStringlyKeyedEnum.ts]
2+
enum AgeGroups { "0-17" , "18-22" , "23-27" , "28-34" , "35-44" , "45-59" , "60-150" }
3+
export const SpotifyAgeGroupEnum = { ...AgeGroups };
4+
5+
//// [declarationEmitSpreadStringlyKeyedEnum.js]
6+
"use strict";
7+
var __assign = (this && this.__assign) || function () {
8+
__assign = Object.assign || function(t) {
9+
for (var s, i = 1, n = arguments.length; i < n; i++) {
10+
s = arguments[i];
11+
for (var p in s) if (Object.prototype.hasOwnProperty.call(s, p))
12+
t[p] = s[p];
13+
}
14+
return t;
15+
};
16+
return __assign.apply(this, arguments);
17+
};
18+
exports.__esModule = true;
19+
exports.SpotifyAgeGroupEnum = void 0;
20+
var AgeGroups;
21+
(function (AgeGroups) {
22+
AgeGroups[AgeGroups["0-17"] = 0] = "0-17";
23+
AgeGroups[AgeGroups["18-22"] = 1] = "18-22";
24+
AgeGroups[AgeGroups["23-27"] = 2] = "23-27";
25+
AgeGroups[AgeGroups["28-34"] = 3] = "28-34";
26+
AgeGroups[AgeGroups["35-44"] = 4] = "35-44";
27+
AgeGroups[AgeGroups["45-59"] = 5] = "45-59";
28+
AgeGroups[AgeGroups["60-150"] = 6] = "60-150";
29+
})(AgeGroups || (AgeGroups = {}));
30+
exports.SpotifyAgeGroupEnum = __assign({}, AgeGroups);
31+
32+
33+
//// [declarationEmitSpreadStringlyKeyedEnum.d.ts]
34+
declare enum AgeGroups {
35+
"0-17" = 0,
36+
"18-22" = 1,
37+
"23-27" = 2,
38+
"28-34" = 3,
39+
"35-44" = 4,
40+
"45-59" = 5,
41+
"60-150" = 6
42+
}
43+
export declare const SpotifyAgeGroupEnum: {
44+
[x: number]: string;
45+
"0-17": typeof AgeGroups["0-17"];
46+
"18-22": typeof AgeGroups["18-22"];
47+
"23-27": typeof AgeGroups["23-27"];
48+
"28-34": typeof AgeGroups["28-34"];
49+
"35-44": typeof AgeGroups["35-44"];
50+
"45-59": typeof AgeGroups["45-59"];
51+
"60-150": typeof AgeGroups["60-150"];
52+
};
53+
export {};
Lines changed: 15 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,15 @@
1+
=== tests/cases/compiler/declarationEmitSpreadStringlyKeyedEnum.ts ===
2+
enum AgeGroups { "0-17" , "18-22" , "23-27" , "28-34" , "35-44" , "45-59" , "60-150" }
3+
>AgeGroups : Symbol(AgeGroups, Decl(declarationEmitSpreadStringlyKeyedEnum.ts, 0, 0))
4+
>"0-17" : Symbol(AgeGroups["0-17"], Decl(declarationEmitSpreadStringlyKeyedEnum.ts, 0, 16))
5+
>"18-22" : Symbol(AgeGroups["18-22"], Decl(declarationEmitSpreadStringlyKeyedEnum.ts, 0, 25))
6+
>"23-27" : Symbol(AgeGroups["23-27"], Decl(declarationEmitSpreadStringlyKeyedEnum.ts, 0, 35))
7+
>"28-34" : Symbol(AgeGroups["28-34"], Decl(declarationEmitSpreadStringlyKeyedEnum.ts, 0, 45))
8+
>"35-44" : Symbol(AgeGroups["35-44"], Decl(declarationEmitSpreadStringlyKeyedEnum.ts, 0, 55))
9+
>"45-59" : Symbol(AgeGroups["45-59"], Decl(declarationEmitSpreadStringlyKeyedEnum.ts, 0, 65))
10+
>"60-150" : Symbol(AgeGroups["60-150"], Decl(declarationEmitSpreadStringlyKeyedEnum.ts, 0, 75))
11+
12+
export const SpotifyAgeGroupEnum = { ...AgeGroups };
13+
>SpotifyAgeGroupEnum : Symbol(SpotifyAgeGroupEnum, Decl(declarationEmitSpreadStringlyKeyedEnum.ts, 1, 12))
14+
>AgeGroups : Symbol(AgeGroups, Decl(declarationEmitSpreadStringlyKeyedEnum.ts, 0, 0))
15+
Lines changed: 16 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,16 @@
1+
=== tests/cases/compiler/declarationEmitSpreadStringlyKeyedEnum.ts ===
2+
enum AgeGroups { "0-17" , "18-22" , "23-27" , "28-34" , "35-44" , "45-59" , "60-150" }
3+
>AgeGroups : AgeGroups
4+
>"0-17" : typeof AgeGroups["0-17"]
5+
>"18-22" : typeof AgeGroups["18-22"]
6+
>"23-27" : typeof AgeGroups["23-27"]
7+
>"28-34" : typeof AgeGroups["28-34"]
8+
>"35-44" : typeof AgeGroups["35-44"]
9+
>"45-59" : typeof AgeGroups["45-59"]
10+
>"60-150" : typeof AgeGroups["60-150"]
11+
12+
export const SpotifyAgeGroupEnum = { ...AgeGroups };
13+
>SpotifyAgeGroupEnum : { [x: number]: string; "0-17": typeof AgeGroups["0-17"]; "18-22": typeof AgeGroups["18-22"]; "23-27": typeof AgeGroups["23-27"]; "28-34": typeof AgeGroups["28-34"]; "35-44": typeof AgeGroups["35-44"]; "45-59": typeof AgeGroups["45-59"]; "60-150": typeof AgeGroups["60-150"]; }
14+
>{ ...AgeGroups } : { [x: number]: string; "0-17": typeof AgeGroups["0-17"]; "18-22": typeof AgeGroups["18-22"]; "23-27": typeof AgeGroups["23-27"]; "28-34": typeof AgeGroups["28-34"]; "35-44": typeof AgeGroups["35-44"]; "45-59": typeof AgeGroups["45-59"]; "60-150": typeof AgeGroups["60-150"]; }
15+
>AgeGroups : typeof AgeGroups
16+

tests/baselines/reference/decrementOperatorWithEnumType.types

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -5,7 +5,7 @@ enum ENUM1 { A, B, "" };
55
>ENUM1 : ENUM1
66
>A : ENUM1.A
77
>B : ENUM1.B
8-
>"" : ENUM1.
8+
>"" : typeof ENUM1[""]
99

1010
// expression
1111
var ResultIsNumber1 = --ENUM1["A"];

tests/baselines/reference/decrementOperatorWithEnumTypeInvalidOperations.types

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -8,7 +8,7 @@ enum ENUM1 { A, B, "" };
88
>ENUM1 : ENUM1
99
>A : ENUM1.A
1010
>B : ENUM1.B
11-
>"" : ENUM1.
11+
>"" : typeof ENUM1[""]
1212

1313
// enum type var
1414
var ResultIsNumber1 = --ENUM;

tests/baselines/reference/deleteOperatorWithEnumType.types

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -8,7 +8,7 @@ enum ENUM1 { A, B, "" };
88
>ENUM1 : ENUM1
99
>A : ENUM1.A
1010
>B : ENUM1.B
11-
>"" : ENUM1.
11+
>"" : typeof ENUM1[""]
1212

1313
// enum type var
1414
var ResultIsBoolean1 = delete ENUM;

tests/baselines/reference/doubleUnderscoreEnumEmit.types

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -7,11 +7,11 @@ enum Foo {
77
>1 : 1
88

99
"(Anonymous function)" = 2,
10-
>"(Anonymous function)" : Foo.(Anonymous function)
10+
>"(Anonymous function)" : typeof Foo["(Anonymous function)"]
1111
>2 : 2
1212

1313
"(Anonymous class)" = 4,
14-
>"(Anonymous class)" : Foo.(Anonymous class)
14+
>"(Anonymous class)" : typeof Foo["(Anonymous class)"]
1515
>4 : 4
1616

1717
"__call" = 10

tests/baselines/reference/enumErrors.types

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -132,11 +132,11 @@ enum E13 {
132132

133133
postColonValueComma: 2,
134134
>postColonValueComma : E13.postColonValueComma
135-
>2 : E13.2
135+
>2 : typeof E13["2"]
136136

137137
postColonValueSemicolon: 3;
138138
>postColonValueSemicolon : E13.postColonValueSemicolon
139-
>3 : E13.3
139+
>3 : typeof E13["3"]
140140

141141
};
142142

@@ -146,7 +146,7 @@ enum E14 { a, b: any "hello" += 1, c, d}
146146
>b : E14.b
147147
>any : E14.any
148148
>"hello" : E14.hello
149-
>1 : E14.1
149+
>1 : typeof E14["1"]
150150
>c : E14.c
151151
>d : E14.d
152152

tests/baselines/reference/enumIdentifierLiterals.types

Lines changed: 5 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -3,17 +3,17 @@ enum Nums {
33
>Nums : Nums
44

55
1.0,
6-
>1.0 : Nums.1
6+
>1.0 : typeof Nums["1"]
77

88
11e-1,
9-
>11e-1 : Nums.1.1
9+
>11e-1 : typeof Nums["1.1"]
1010

1111
0.12e1,
12-
>0.12e1 : Nums.1.2
12+
>0.12e1 : typeof Nums["1.2"]
1313

1414
"13e-1",
15-
>"13e-1" : Nums.13e-1
15+
>"13e-1" : typeof Nums["13e-1"]
1616

1717
0xF00D
18-
>0xF00D : Nums.61453
18+
>0xF00D : typeof Nums["61453"]
1919
}

tests/baselines/reference/enumWithNegativeInfinityProperty.types

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -3,7 +3,7 @@ enum A {
33
>A : A
44

55
"-Infinity" = 1
6-
>"-Infinity" : A.-Infinity
6+
>"-Infinity" : typeof A["-Infinity"]
77
>1 : 1
88
}
99

tests/baselines/reference/enumWithQuotedElementName1.types

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -3,5 +3,5 @@ enum E {
33
>E : E
44

55
'fo"o',
6-
>'fo"o' : E.fo"o
6+
>'fo"o' : typeof E["fo\"o"]
77
}

tests/baselines/reference/enumWithQuotedElementName2.types

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -3,5 +3,5 @@ enum E {
33
>E : E
44

55
"fo'o",
6-
>"fo'o" : E.fo'o
6+
>"fo'o" : typeof E["fo'o"]
77
}

tests/baselines/reference/enumWithUnicodeEscape1.types

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -3,6 +3,6 @@ enum E {
33
>E : E
44

55
'gold \u2730'
6-
>'gold \u2730' : E.gold
6+
>'gold \u2730' : typeof E["gold \u2730"]
77
}
88

tests/baselines/reference/incrementOperatorWithEnumType.types

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -5,7 +5,7 @@ enum ENUM1 { A, B, "" };
55
>ENUM1 : ENUM1
66
>A : ENUM1.A
77
>B : ENUM1.B
8-
>"" : ENUM1.
8+
>"" : typeof ENUM1[""]
99

1010
// expression
1111
var ResultIsNumber1 = ++ENUM1["B"];

tests/baselines/reference/incrementOperatorWithEnumTypeInvalidOperations.types

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -8,7 +8,7 @@ enum ENUM1 { A, B, "" };
88
>ENUM1 : ENUM1
99
>A : ENUM1.A
1010
>B : ENUM1.B
11-
>"" : ENUM1.
11+
>"" : typeof ENUM1[""]
1212

1313
// enum type var
1414
var ResultIsNumber1 = ++ENUM;

tests/baselines/reference/literalsInComputedProperties1.types

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -161,20 +161,20 @@ enum X {
161161
>X : X
162162

163163
1 = 1,
164-
>1 : X.1
164+
>1 : typeof X["1"]
165165
>1 : 1
166166

167167
[2] = 2,
168-
>[2] : X.2
168+
>[2] : typeof X["2"]
169169
>2 : 2
170170
>2 : 2
171171

172172
"3" = 3,
173-
>"3" : X.3
173+
>"3" : typeof X["3"]
174174
>3 : 3
175175

176176
["4"] = 4,
177-
>["4"] : X.4
177+
>["4"] : typeof X["4"]
178178
>"4" : "4"
179179
>4 : 4
180180

tests/baselines/reference/negateOperatorWithEnumType.types

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -8,7 +8,7 @@ enum ENUM1 { A, B, "" };
88
>ENUM1 : ENUM1
99
>A : ENUM1.A
1010
>B : ENUM1.B
11-
>"" : ENUM1.
11+
>"" : typeof ENUM1[""]
1212

1313
// enum type var
1414
var ResultIsNumber1 = -ENUM;
@@ -32,7 +32,7 @@ var ResultIsNumber3 = -(ENUM1.B + ENUM1[""]);
3232
>ENUM1.B : ENUM1.B
3333
>ENUM1 : typeof ENUM1
3434
>B : ENUM1.B
35-
>ENUM1[""] : ENUM1.
35+
>ENUM1[""] : typeof ENUM1[""]
3636
>ENUM1 : typeof ENUM1
3737
>"" : ""
3838

tests/baselines/reference/parserEnum5.types

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -6,13 +6,13 @@ enum E2 { a, }
66
enum E3 { a: 1, }
77
>E3 : E3
88
>a : E3.a
9-
>1 : E3.1
9+
>1 : typeof E3["1"]
1010

1111
enum E1 { a, b: 1, c, d: 2 = 3 }
1212
>E1 : E1
1313
>a : E1.a
1414
>b : E1.b
15-
>1 : E1.1
15+
>1 : typeof E1["1"]
1616
>c : E1.c
1717
>d : E1.d
1818
>2 : E1.c

tests/baselines/reference/parserEnum7.types

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -3,7 +3,7 @@ enum E {
33
>E : E
44

55
1, 2, 3
6-
>1 : E.1
7-
>2 : E.2
8-
>3 : E.3
6+
>1 : typeof E["1"]
7+
>2 : typeof E["2"]
8+
>3 : typeof E["3"]
99
}

tests/baselines/reference/plusOperatorWithEnumType.types

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -8,7 +8,7 @@ enum ENUM1 { A, B, "" };
88
>ENUM1 : ENUM1
99
>A : ENUM1.A
1010
>B : ENUM1.B
11-
>"" : ENUM1.
11+
>"" : typeof ENUM1[""]
1212

1313
// enum type var
1414
var ResultIsNumber1 = +ENUM;

tests/baselines/reference/typeofOperatorWithEnumType.types

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -8,7 +8,7 @@ enum ENUM1 { A, B, "" };
88
>ENUM1 : ENUM1
99
>A : ENUM1.A
1010
>B : ENUM1.B
11-
>"" : ENUM1.
11+
>"" : typeof ENUM1[""]
1212

1313
// enum type var
1414
var ResultIsString1 = typeof ENUM;

tests/baselines/reference/voidOperatorWithEnumType.types

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -8,7 +8,7 @@ enum ENUM1 { A, B, "" };
88
>ENUM1 : ENUM1
99
>A : ENUM1.A
1010
>B : ENUM1.B
11-
>"" : ENUM1.
11+
>"" : typeof ENUM1[""]
1212

1313
// enum type var
1414
var ResultIsAny1 = void ENUM;
Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,3 @@
1+
// @declaration: true
2+
enum AgeGroups { "0-17" , "18-22" , "23-27" , "28-34" , "35-44" , "45-59" , "60-150" }
3+
export const SpotifyAgeGroupEnum = { ...AgeGroups };

0 commit comments

Comments
 (0)