From c7ef14cc916544f8b3d0144d3c3aad485810b77e Mon Sep 17 00:00:00 2001 From: Collins Abitekaniza Date: Mon, 5 Nov 2018 19:57:13 +0300 Subject: [PATCH 1/5] prohibit mutation for Number + String literal types --- src/compiler/checker.ts | 21 +++++++++++++++++++-- src/compiler/diagnosticMessages.json | 4 ++++ src/compiler/utilities.ts | 15 +++++++++++++++ 3 files changed, 38 insertions(+), 2 deletions(-) diff --git a/src/compiler/checker.ts b/src/compiler/checker.ts index ffa7a69fbd893..1120f01c9ad4c 100644 --- a/src/compiler/checker.ts +++ b/src/compiler/checker.ts @@ -21803,7 +21803,16 @@ namespace ts { } function checkPostfixUnaryExpression(node: PostfixUnaryExpression): Type { - const operandType = checkExpression(node.operand); + let operandType: Type; + const symbol = (node.operand).escapedText ? getResolvedSymbol(node.operand as Identifier) : undefined; + if (symbol && !(getDeclarationNodeFlagsFromSymbol(symbol) & NodeFlags.Const)) { + operandType = getTypeOfSymbol(symbol); + if (isLiteralType(operandType) && !(operandType.flags & (TypeFlags.EnumLike | TypeFlags.BooleanLike | TypeFlags.Undefined))) { + error(node.operand, Diagnostics.The_literal_type_0_cannot_be_modified, typeToString(operandType)); + } + } + operandType = checkExpression(node.operand); + if (operandType === silentNeverType) { return silentNeverType; } @@ -22170,10 +22179,18 @@ namespace ts { function checkBinaryLikeExpression(left: Expression, operatorToken: Node, right: Expression, checkMode?: CheckMode, errorNode?: Node): Type { const operator = operatorToken.kind; + let leftType: Type; + + const symbol = (left).escapedText ? getResolvedSymbol(left as Identifier) : undefined; + if (symbol && isCompoundAssignmentOperator(operator) && !(getDeclarationNodeFlagsFromSymbol(symbol) & NodeFlags.Const)) { + leftType = getTypeOfSymbol(getResolvedSymbol(left as Identifier)); + if (isLiteralType(leftType) && !(leftType.flags & (TypeFlags.EnumLike | TypeFlags.BooleanLike | TypeFlags.Undefined))) { + error(left, Diagnostics.The_literal_type_0_cannot_be_modified, typeToString(leftType)); + } + } if (operator === SyntaxKind.EqualsToken && (left.kind === SyntaxKind.ObjectLiteralExpression || left.kind === SyntaxKind.ArrayLiteralExpression)) { return checkDestructuringAssignment(left, checkExpression(right, checkMode), checkMode, right.kind === SyntaxKind.ThisKeyword); } - let leftType: Type; if (operator === SyntaxKind.AmpersandAmpersandToken || operator === SyntaxKind.BarBarToken) { leftType = checkTruthinessExpression(left, checkMode); } diff --git a/src/compiler/diagnosticMessages.json b/src/compiler/diagnosticMessages.json index e3f8e1a7ad5a6..64509c64eb3e3 100644 --- a/src/compiler/diagnosticMessages.json +++ b/src/compiler/diagnosticMessages.json @@ -2529,6 +2529,10 @@ "category": "Error", "code": 2742 }, + "The literal type '{0}' cannot be modified.": { + "category": "Error", + "code": 2743 + }, "Import declaration '{0}' is using private name '{1}'.": { "category": "Error", diff --git a/src/compiler/utilities.ts b/src/compiler/utilities.ts index 6b1778aab3050..8abce4f3fd1d4 100644 --- a/src/compiler/utilities.ts +++ b/src/compiler/utilities.ts @@ -3839,6 +3839,21 @@ namespace ts { || token === SyntaxKind.ExclamationToken; } + export function isCompoundAssignmentOperator(token: SyntaxKind): boolean { + return token === SyntaxKind.PlusEqualsToken + || token === SyntaxKind.MinusEqualsToken + || token === SyntaxKind.AsteriskAsteriskEqualsToken + || token === SyntaxKind.AsteriskEqualsToken + || token === SyntaxKind.SlashEqualsToken + || token === SyntaxKind.PercentEqualsToken + || token === SyntaxKind.AmpersandEqualsToken + || token === SyntaxKind.BarEqualsToken + || token === SyntaxKind.CaretEqualsToken + || token === SyntaxKind.LessThanLessThanEqualsToken + || token === SyntaxKind.GreaterThanGreaterThanGreaterThanEqualsToken + || token === SyntaxKind.GreaterThanGreaterThanEqualsToken; + } + export function isAssignmentOperator(token: SyntaxKind): boolean { return token >= SyntaxKind.FirstAssignment && token <= SyntaxKind.LastAssignment; } From 00844bb838b3f9efe7aa050dc492402f35c5ae69 Mon Sep 17 00:00:00 2001 From: Collins Abitekaniza Date: Mon, 5 Nov 2018 21:34:51 +0300 Subject: [PATCH 2/5] refactor + add new baseline tests --- src/compiler/checker.ts | 2 +- src/compiler/utilities.ts | 2 +- .../reference/enumLiteralTypes1.errors.txt | 119 +++++++++++ .../reference/numericLiteralTypes1.errors.txt | 148 +++++++++++++ .../reference/numericLiteralTypes2.errors.txt | 148 +++++++++++++ .../reference/numericLiteralTypes4.errors.txt | 165 ++++++++++++++ .../reference/numericLiteralTypes4.js | 90 ++++++++ .../reference/numericLiteralTypes4.symbols | 127 +++++++++++ .../reference/numericLiteralTypes4.types | 202 ++++++++++++++++++ .../reference/stringLiteralTypes4.errors.txt | 8 + .../reference/stringLiteralTypes4.js | 7 + .../reference/stringLiteralTypes4.symbols | 7 + .../reference/stringLiteralTypes4.types | 10 + .../types/literal/numericLiteralTypes4.ts | 45 ++++ .../types/literal/stringLiteralTypes4.ts | 2 + 15 files changed, 1080 insertions(+), 2 deletions(-) create mode 100644 tests/baselines/reference/enumLiteralTypes1.errors.txt create mode 100644 tests/baselines/reference/numericLiteralTypes1.errors.txt create mode 100644 tests/baselines/reference/numericLiteralTypes2.errors.txt create mode 100644 tests/baselines/reference/numericLiteralTypes4.errors.txt create mode 100644 tests/baselines/reference/numericLiteralTypes4.js create mode 100644 tests/baselines/reference/numericLiteralTypes4.symbols create mode 100644 tests/baselines/reference/numericLiteralTypes4.types create mode 100644 tests/baselines/reference/stringLiteralTypes4.errors.txt create mode 100644 tests/baselines/reference/stringLiteralTypes4.js create mode 100644 tests/baselines/reference/stringLiteralTypes4.symbols create mode 100644 tests/baselines/reference/stringLiteralTypes4.types create mode 100644 tests/cases/conformance/types/literal/numericLiteralTypes4.ts create mode 100644 tests/cases/conformance/types/literal/stringLiteralTypes4.ts diff --git a/src/compiler/checker.ts b/src/compiler/checker.ts index 1120f01c9ad4c..9e19b92677ff6 100644 --- a/src/compiler/checker.ts +++ b/src/compiler/checker.ts @@ -21810,7 +21810,7 @@ namespace ts { if (isLiteralType(operandType) && !(operandType.flags & (TypeFlags.EnumLike | TypeFlags.BooleanLike | TypeFlags.Undefined))) { error(node.operand, Diagnostics.The_literal_type_0_cannot_be_modified, typeToString(operandType)); } - } + } operandType = checkExpression(node.operand); if (operandType === silentNeverType) { diff --git a/src/compiler/utilities.ts b/src/compiler/utilities.ts index 8abce4f3fd1d4..dd2e7eae5b36c 100644 --- a/src/compiler/utilities.ts +++ b/src/compiler/utilities.ts @@ -3840,7 +3840,7 @@ namespace ts { } export function isCompoundAssignmentOperator(token: SyntaxKind): boolean { - return token === SyntaxKind.PlusEqualsToken + return token === SyntaxKind.PlusEqualsToken || token === SyntaxKind.MinusEqualsToken || token === SyntaxKind.AsteriskAsteriskEqualsToken || token === SyntaxKind.AsteriskEqualsToken diff --git a/tests/baselines/reference/enumLiteralTypes1.errors.txt b/tests/baselines/reference/enumLiteralTypes1.errors.txt new file mode 100644 index 0000000000000..804b851aff32f --- /dev/null +++ b/tests/baselines/reference/enumLiteralTypes1.errors.txt @@ -0,0 +1,119 @@ +tests/cases/conformance/types/literal/enumLiteralTypes1.ts(44,5): error TS2736: The literal type 'YesNo' cannot be modified. + + +==== tests/cases/conformance/types/literal/enumLiteralTypes1.ts (1 errors) ==== + const enum Choice { Unknown, Yes, No }; + + type YesNo = Choice.Yes | Choice.No; + type NoYes = Choice.No | Choice.Yes; + type UnknownYesNo = Choice.Unknown | Choice.Yes | Choice.No; + + function f1() { + var a: YesNo; + var a: NoYes; + var a: Choice.Yes | Choice.No; + var a: Choice.No | Choice.Yes; + } + + function f2(a: YesNo, b: UnknownYesNo, c: Choice) { + b = a; + c = a; + c = b; + } + + function f3(a: Choice.Yes, b: YesNo) { + var x = a + b; + var x = a - b; + var x = a * b; + var x = a / b; + var x = a % b; + var x = a | b; + var x = a & b; + var x = a ^ b; + var x = -b; + var x = ~b; + var y = a == b; + var y = a != b; + var y = a === b; + var y = a !== b; + var y = a > b; + var y = a < b; + var y = a >= b; + var y = a <= b; + var y = !b; + } + + function f4(a: Choice.Yes, b: YesNo) { + a++; + b++; + ~ +!!! error TS2736: The literal type 'YesNo' cannot be modified. + } + + declare function g(x: Choice.Yes): string; + declare function g(x: Choice.No): boolean; + declare function g(x: Choice): number; + + function f5(a: YesNo, b: UnknownYesNo, c: Choice) { + var z1 = g(Choice.Yes); + var z2 = g(Choice.No); + var z3 = g(a); + var z4 = g(b); + var z5 = g(c); + } + + function assertNever(x: never): never { + throw new Error("Unexpected value"); + } + + function f10(x: YesNo) { + switch (x) { + case Choice.Yes: return "true"; + case Choice.No: return "false"; + } + } + + function f11(x: YesNo) { + switch (x) { + case Choice.Yes: return "true"; + case Choice.No: return "false"; + } + return assertNever(x); + } + + function f12(x: UnknownYesNo) { + if (x) { + x; + } + else { + x; + } + } + + function f13(x: UnknownYesNo) { + if (x === Choice.Yes) { + x; + } + else { + x; + } + } + + type Item = + { kind: Choice.Yes, a: string } | + { kind: Choice.No, b: string }; + + function f20(x: Item) { + switch (x.kind) { + case Choice.Yes: return x.a; + case Choice.No: return x.b; + } + } + + function f21(x: Item) { + switch (x.kind) { + case Choice.Yes: return x.a; + case Choice.No: return x.b; + } + return assertNever(x); + } \ No newline at end of file diff --git a/tests/baselines/reference/numericLiteralTypes1.errors.txt b/tests/baselines/reference/numericLiteralTypes1.errors.txt new file mode 100644 index 0000000000000..f8a02a0b5a28f --- /dev/null +++ b/tests/baselines/reference/numericLiteralTypes1.errors.txt @@ -0,0 +1,148 @@ +tests/cases/conformance/types/literal/numericLiteralTypes1.ts(48,5): error TS2736: The literal type '1' cannot be modified. +tests/cases/conformance/types/literal/numericLiteralTypes1.ts(49,5): error TS2736: The literal type '0 | 1 | 2' cannot be modified. + + +==== tests/cases/conformance/types/literal/numericLiteralTypes1.ts (2 errors) ==== + type A1 = 1; + type A2 = 1.0; + type A3 = 1e0; + type A4 = 10e-1; + type A5 = 1 | 1.0 | 1e0 | 10e-1; + + function f1() { + var a: A1 = 1; + var a: A2 = 1; + var a: A3 = 1; + var a: A4 = 1; + var a: A5 = 1; + } + + type B1 = -1 | 0 | 1; + type B2 = 1 | 0 | -1; + type B3 = 0 | -1 | 1; + + function f2() { + var b: B1 = -1; + var b: B2 = 0; + var b: B3 = 1; + } + + function f3(a: 1, b: 0 | 1 | 2) { + var x = a + b; + var x = a - b; + var x = a * b; + var x = a / b; + var x = a % b; + var x = a | b; + var x = a & b; + var x = a ^ b; + var x = -b; + var x = ~b; + var y = a == b; + var y = a != b; + var y = a === b; + var y = a !== b; + var y = a > b; + var y = a < b; + var y = a >= b; + var y = a <= b; + var y = !b; + } + + function f4(a: 1, b: 0 | 1 | 2) { + a++; + ~ +!!! error TS2736: The literal type '1' cannot be modified. + b++; + ~ +!!! error TS2736: The literal type '0 | 1 | 2' cannot be modified. + } + + declare function g(x: 0): string; + declare function g(x: 1): boolean; + declare function g(x: number): number; + + function f5(a: 1, b: 0 | 1 | 2) { + var z1 = g(0); + var z2 = g(1); + var z3 = g(2); + var z4 = g(a); + var z5 = g(b); + } + + function assertNever(x: never): never { + throw new Error("Unexpected value"); + } + + type Tag = 0 | 1 | 2; + + function f10(x: Tag) { + switch (x) { + case 0: return "a"; + case 1: return "b"; + case 2: return "c"; + } + } + + function f11(x: Tag) { + switch (x) { + case 0: return "a"; + case 1: return "b"; + case 2: return "c"; + } + return assertNever(x); + } + + function f12(x: Tag) { + if (x) { + x; + } + else { + x; + } + } + + function f13(x: Tag) { + if (x === 0 || x === 2) { + x; + } + else { + x; + } + } + + function f14(x: 0 | 1 | 2, y: string) { + var a = x && y; + var b = x || y; + } + + function f15(x: 0 | false, y: 1 | "one") { + var a = x && y; + var b = y && x; + var c = x || y; + var d = y || x; + var e = !x; + var f = !y; + } + + type Item = + { kind: 0, a: string } | + { kind: 1, b: string } | + { kind: 2, c: string }; + + function f20(x: Item) { + switch (x.kind) { + case 0: return x.a; + case 1: return x.b; + case 2: return x.c; + } + } + + function f21(x: Item) { + switch (x.kind) { + case 0: return x.a; + case 1: return x.b; + case 2: return x.c; + } + return assertNever(x); + } \ No newline at end of file diff --git a/tests/baselines/reference/numericLiteralTypes2.errors.txt b/tests/baselines/reference/numericLiteralTypes2.errors.txt new file mode 100644 index 0000000000000..5e35ca42fdea4 --- /dev/null +++ b/tests/baselines/reference/numericLiteralTypes2.errors.txt @@ -0,0 +1,148 @@ +tests/cases/conformance/types/literal/numericLiteralTypes2.ts(48,5): error TS2736: The literal type '1' cannot be modified. +tests/cases/conformance/types/literal/numericLiteralTypes2.ts(49,5): error TS2736: The literal type '0 | 1 | 2' cannot be modified. + + +==== tests/cases/conformance/types/literal/numericLiteralTypes2.ts (2 errors) ==== + type A1 = 1; + type A2 = 1.0; + type A3 = 1e0; + type A4 = 10e-1; + type A5 = 1 | 1.0 | 1e0 | 10e-1; + + function f1() { + var a: A1 = 1; + var a: A2 = 1; + var a: A3 = 1; + var a: A4 = 1; + var a: A5 = 1; + } + + type B1 = -1 | 0 | 1; + type B2 = 1 | 0 | -1; + type B3 = 0 | -1 | 1; + + function f2() { + var b: B1 = -1; + var b: B2 = 0; + var b: B3 = 1; + } + + function f3(a: 1, b: 0 | 1 | 2) { + var x = a + b; + var x = a - b; + var x = a * b; + var x = a / b; + var x = a % b; + var x = a | b; + var x = a & b; + var x = a ^ b; + var x = -b; + var x = ~b; + var y = a == b; + var y = a != b; + var y = a === b; + var y = a !== b; + var y = a > b; + var y = a < b; + var y = a >= b; + var y = a <= b; + var y = !b; + } + + function f4(a: 1, b: 0 | 1 | 2) { + a++; + ~ +!!! error TS2736: The literal type '1' cannot be modified. + b++; + ~ +!!! error TS2736: The literal type '0 | 1 | 2' cannot be modified. + } + + declare function g(x: 0): string; + declare function g(x: 1): boolean; + declare function g(x: number): number; + + function f5(a: 1, b: 0 | 1 | 2) { + var z1 = g(0); + var z2 = g(1); + var z3 = g(2); + var z4 = g(a); + var z5 = g(b); + } + + function assertNever(x: never): never { + throw new Error("Unexpected value"); + } + + type Tag = 0 | 1 | 2; + + function f10(x: Tag) { + switch (x) { + case 0: return "a"; + case 1: return "b"; + case 2: return "c"; + } + } + + function f11(x: Tag) { + switch (x) { + case 0: return "a"; + case 1: return "b"; + case 2: return "c"; + } + return assertNever(x); + } + + function f12(x: Tag) { + if (x) { + x; + } + else { + x; + } + } + + function f13(x: Tag) { + if (x === 0 || x === 2) { + x; + } + else { + x; + } + } + + function f14(x: 0 | 1 | 2, y: string) { + var a = x && y; + var b = x || y; + } + + function f15(x: 0 | false, y: 1 | "one") { + var a = x && y; + var b = y && x; + var c = x || y; + var d = y || x; + var e = !x; + var f = !y; + } + + type Item = + { kind: 0, a: string } | + { kind: 1, b: string } | + { kind: 2, c: string }; + + function f20(x: Item) { + switch (x.kind) { + case 0: return x.a; + case 1: return x.b; + case 2: return x.c; + } + } + + function f21(x: Item) { + switch (x.kind) { + case 0: return x.a; + case 1: return x.b; + case 2: return x.c; + } + return assertNever(x); + } \ No newline at end of file diff --git a/tests/baselines/reference/numericLiteralTypes4.errors.txt b/tests/baselines/reference/numericLiteralTypes4.errors.txt new file mode 100644 index 0000000000000..c2daf69198d75 --- /dev/null +++ b/tests/baselines/reference/numericLiteralTypes4.errors.txt @@ -0,0 +1,165 @@ +tests/cases/conformance/types/literal/numericLiteralTypes4.ts(5,1): error TS2736: The literal type '10' cannot be modified. +tests/cases/conformance/types/literal/numericLiteralTypes4.ts(6,1): error TS2736: The literal type '10' cannot be modified. +tests/cases/conformance/types/literal/numericLiteralTypes4.ts(7,1): error TS2736: The literal type '10' cannot be modified. +tests/cases/conformance/types/literal/numericLiteralTypes4.ts(8,1): error TS2736: The literal type '10' cannot be modified. +tests/cases/conformance/types/literal/numericLiteralTypes4.ts(9,1): error TS2736: The literal type '10' cannot be modified. +tests/cases/conformance/types/literal/numericLiteralTypes4.ts(10,1): error TS2736: The literal type '10' cannot be modified. +tests/cases/conformance/types/literal/numericLiteralTypes4.ts(11,1): error TS2736: The literal type '10' cannot be modified. +tests/cases/conformance/types/literal/numericLiteralTypes4.ts(12,1): error TS2736: The literal type '10' cannot be modified. +tests/cases/conformance/types/literal/numericLiteralTypes4.ts(13,1): error TS2736: The literal type '10' cannot be modified. +tests/cases/conformance/types/literal/numericLiteralTypes4.ts(14,1): error TS2736: The literal type '10' cannot be modified. +tests/cases/conformance/types/literal/numericLiteralTypes4.ts(15,1): error TS2736: The literal type '10' cannot be modified. +tests/cases/conformance/types/literal/numericLiteralTypes4.ts(16,1): error TS2736: The literal type '10' cannot be modified. +tests/cases/conformance/types/literal/numericLiteralTypes4.ts(17,1): error TS2736: The literal type '10' cannot be modified. +tests/cases/conformance/types/literal/numericLiteralTypes4.ts(19,1): error TS2736: The literal type '10 | 11' cannot be modified. +tests/cases/conformance/types/literal/numericLiteralTypes4.ts(20,1): error TS2736: The literal type '10 | 11' cannot be modified. +tests/cases/conformance/types/literal/numericLiteralTypes4.ts(21,1): error TS2736: The literal type '10 | 11' cannot be modified. +tests/cases/conformance/types/literal/numericLiteralTypes4.ts(22,1): error TS2736: The literal type '10 | 11' cannot be modified. +tests/cases/conformance/types/literal/numericLiteralTypes4.ts(23,1): error TS2736: The literal type '10 | 11' cannot be modified. +tests/cases/conformance/types/literal/numericLiteralTypes4.ts(24,1): error TS2736: The literal type '10 | 11' cannot be modified. +tests/cases/conformance/types/literal/numericLiteralTypes4.ts(25,1): error TS2736: The literal type '10 | 11' cannot be modified. +tests/cases/conformance/types/literal/numericLiteralTypes4.ts(26,1): error TS2736: The literal type '10 | 11' cannot be modified. +tests/cases/conformance/types/literal/numericLiteralTypes4.ts(27,1): error TS2736: The literal type '10 | 11' cannot be modified. +tests/cases/conformance/types/literal/numericLiteralTypes4.ts(28,1): error TS2736: The literal type '10 | 11' cannot be modified. +tests/cases/conformance/types/literal/numericLiteralTypes4.ts(29,1): error TS2736: The literal type '10 | 11' cannot be modified. +tests/cases/conformance/types/literal/numericLiteralTypes4.ts(30,1): error TS2736: The literal type '10 | 11' cannot be modified. +tests/cases/conformance/types/literal/numericLiteralTypes4.ts(31,1): error TS2736: The literal type '10 | 11' cannot be modified. +tests/cases/conformance/types/literal/numericLiteralTypes4.ts(33,1): error TS2736: The literal type '10 | 11 | 12' cannot be modified. +tests/cases/conformance/types/literal/numericLiteralTypes4.ts(34,1): error TS2736: The literal type '10 | 11 | 12' cannot be modified. +tests/cases/conformance/types/literal/numericLiteralTypes4.ts(35,1): error TS2736: The literal type '10 | 11 | 12' cannot be modified. +tests/cases/conformance/types/literal/numericLiteralTypes4.ts(36,1): error TS2736: The literal type '10 | 11 | 12' cannot be modified. +tests/cases/conformance/types/literal/numericLiteralTypes4.ts(37,1): error TS2736: The literal type '10 | 11 | 12' cannot be modified. +tests/cases/conformance/types/literal/numericLiteralTypes4.ts(38,1): error TS2736: The literal type '10 | 11 | 12' cannot be modified. +tests/cases/conformance/types/literal/numericLiteralTypes4.ts(39,1): error TS2736: The literal type '10 | 11 | 12' cannot be modified. +tests/cases/conformance/types/literal/numericLiteralTypes4.ts(40,1): error TS2736: The literal type '10 | 11 | 12' cannot be modified. +tests/cases/conformance/types/literal/numericLiteralTypes4.ts(41,1): error TS2736: The literal type '10 | 11 | 12' cannot be modified. +tests/cases/conformance/types/literal/numericLiteralTypes4.ts(42,1): error TS2736: The literal type '10 | 11 | 12' cannot be modified. +tests/cases/conformance/types/literal/numericLiteralTypes4.ts(43,1): error TS2736: The literal type '10 | 11 | 12' cannot be modified. +tests/cases/conformance/types/literal/numericLiteralTypes4.ts(44,1): error TS2736: The literal type '10 | 11 | 12' cannot be modified. +tests/cases/conformance/types/literal/numericLiteralTypes4.ts(45,1): error TS2736: The literal type '10 | 11 | 12' cannot be modified. + + +==== tests/cases/conformance/types/literal/numericLiteralTypes4.ts (39 errors) ==== + var a: 10 = 10; + var b: 10 | 11 = 11; + var c: 10 | 11 | 12 = 10; + + a ++; + ~ +!!! error TS2736: The literal type '10' cannot be modified. + a --; + ~ +!!! error TS2736: The literal type '10' cannot be modified. + a += 1; + ~ +!!! error TS2736: The literal type '10' cannot be modified. + a -= 1; + ~ +!!! error TS2736: The literal type '10' cannot be modified. + a *= 1; + ~ +!!! error TS2736: The literal type '10' cannot be modified. + a /= 1; + ~ +!!! error TS2736: The literal type '10' cannot be modified. + a %= 1; + ~ +!!! error TS2736: The literal type '10' cannot be modified. + a &= 1; + ~ +!!! error TS2736: The literal type '10' cannot be modified. + a |= 1; + ~ +!!! error TS2736: The literal type '10' cannot be modified. + a ^= 1; + ~ +!!! error TS2736: The literal type '10' cannot be modified. + a >>= 1; + ~ +!!! error TS2736: The literal type '10' cannot be modified. + a >>>= 1; + ~ +!!! error TS2736: The literal type '10' cannot be modified. + a <<= 1; + ~ +!!! error TS2736: The literal type '10' cannot be modified. + + b ++; + ~ +!!! error TS2736: The literal type '10 | 11' cannot be modified. + b --; + ~ +!!! error TS2736: The literal type '10 | 11' cannot be modified. + b += 1; + ~ +!!! error TS2736: The literal type '10 | 11' cannot be modified. + b -= 1; + ~ +!!! error TS2736: The literal type '10 | 11' cannot be modified. + b *= 1; + ~ +!!! error TS2736: The literal type '10 | 11' cannot be modified. + b /= 1; + ~ +!!! error TS2736: The literal type '10 | 11' cannot be modified. + b %= 1; + ~ +!!! error TS2736: The literal type '10 | 11' cannot be modified. + b &= 1; + ~ +!!! error TS2736: The literal type '10 | 11' cannot be modified. + b |= 1; + ~ +!!! error TS2736: The literal type '10 | 11' cannot be modified. + b ^= 1; + ~ +!!! error TS2736: The literal type '10 | 11' cannot be modified. + b >>= 1; + ~ +!!! error TS2736: The literal type '10 | 11' cannot be modified. + b >>>= 1; + ~ +!!! error TS2736: The literal type '10 | 11' cannot be modified. + b <<= 1; + ~ +!!! error TS2736: The literal type '10 | 11' cannot be modified. + + c ++; + ~ +!!! error TS2736: The literal type '10 | 11 | 12' cannot be modified. + c --; + ~ +!!! error TS2736: The literal type '10 | 11 | 12' cannot be modified. + c += 1; + ~ +!!! error TS2736: The literal type '10 | 11 | 12' cannot be modified. + c -= 1; + ~ +!!! error TS2736: The literal type '10 | 11 | 12' cannot be modified. + c *= 1; + ~ +!!! error TS2736: The literal type '10 | 11 | 12' cannot be modified. + c /= 1; + ~ +!!! error TS2736: The literal type '10 | 11 | 12' cannot be modified. + c %= 1; + ~ +!!! error TS2736: The literal type '10 | 11 | 12' cannot be modified. + c &= 1; + ~ +!!! error TS2736: The literal type '10 | 11 | 12' cannot be modified. + c |= 1; + ~ +!!! error TS2736: The literal type '10 | 11 | 12' cannot be modified. + c ^= 1; + ~ +!!! error TS2736: The literal type '10 | 11 | 12' cannot be modified. + c >>= 1; + ~ +!!! error TS2736: The literal type '10 | 11 | 12' cannot be modified. + c >>>= 1; + ~ +!!! error TS2736: The literal type '10 | 11 | 12' cannot be modified. + c <<= 1; + ~ +!!! error TS2736: The literal type '10 | 11 | 12' cannot be modified. \ No newline at end of file diff --git a/tests/baselines/reference/numericLiteralTypes4.js b/tests/baselines/reference/numericLiteralTypes4.js new file mode 100644 index 0000000000000..0fc979a832fbe --- /dev/null +++ b/tests/baselines/reference/numericLiteralTypes4.js @@ -0,0 +1,90 @@ +//// [numericLiteralTypes4.ts] +var a: 10 = 10; +var b: 10 | 11 = 11; +var c: 10 | 11 | 12 = 10; + +a ++; +a --; +a += 1; +a -= 1; +a *= 1; +a /= 1; +a %= 1; +a &= 1; +a |= 1; +a ^= 1; +a >>= 1; +a >>>= 1; +a <<= 1; + +b ++; +b --; +b += 1; +b -= 1; +b *= 1; +b /= 1; +b %= 1; +b &= 1; +b |= 1; +b ^= 1; +b >>= 1; +b >>>= 1; +b <<= 1; + +c ++; +c --; +c += 1; +c -= 1; +c *= 1; +c /= 1; +c %= 1; +c &= 1; +c |= 1; +c ^= 1; +c >>= 1; +c >>>= 1; +c <<= 1; + +//// [numericLiteralTypes4.js] +var a = 10; +var b = 11; +var c = 10; +a++; +a--; +a += 1; +a -= 1; +a *= 1; +a /= 1; +a %= 1; +a &= 1; +a |= 1; +a ^= 1; +a >>= 1; +a >>>= 1; +a <<= 1; +b++; +b--; +b += 1; +b -= 1; +b *= 1; +b /= 1; +b %= 1; +b &= 1; +b |= 1; +b ^= 1; +b >>= 1; +b >>>= 1; +b <<= 1; +c++; +c--; +c += 1; +c -= 1; +c *= 1; +c /= 1; +c %= 1; +c &= 1; +c |= 1; +c ^= 1; +c >>= 1; +c >>>= 1; +c <<= 1; diff --git a/tests/baselines/reference/numericLiteralTypes4.symbols b/tests/baselines/reference/numericLiteralTypes4.symbols new file mode 100644 index 0000000000000..4d9705b0f0207 --- /dev/null +++ b/tests/baselines/reference/numericLiteralTypes4.symbols @@ -0,0 +1,127 @@ +=== tests/cases/conformance/types/literal/numericLiteralTypes4.ts === +var a: 10 = 10; +>a : Symbol(a, Decl(numericLiteralTypes4.ts, 0, 3)) + +var b: 10 | 11 = 11; +>b : Symbol(b, Decl(numericLiteralTypes4.ts, 1, 3)) + +var c: 10 | 11 | 12 = 10; +>c : Symbol(c, Decl(numericLiteralTypes4.ts, 2, 3)) + +a ++; +>a : Symbol(a, Decl(numericLiteralTypes4.ts, 0, 3)) + +a --; +>a : Symbol(a, Decl(numericLiteralTypes4.ts, 0, 3)) + +a += 1; +>a : Symbol(a, Decl(numericLiteralTypes4.ts, 0, 3)) + +a -= 1; +>a : Symbol(a, Decl(numericLiteralTypes4.ts, 0, 3)) + +a *= 1; +>a : Symbol(a, Decl(numericLiteralTypes4.ts, 0, 3)) + +a /= 1; +>a : Symbol(a, Decl(numericLiteralTypes4.ts, 0, 3)) + +a %= 1; +>a : Symbol(a, Decl(numericLiteralTypes4.ts, 0, 3)) + +a &= 1; +>a : Symbol(a, Decl(numericLiteralTypes4.ts, 0, 3)) + +a |= 1; +>a : Symbol(a, Decl(numericLiteralTypes4.ts, 0, 3)) + +a ^= 1; +>a : Symbol(a, Decl(numericLiteralTypes4.ts, 0, 3)) + +a >>= 1; +>a : Symbol(a, Decl(numericLiteralTypes4.ts, 0, 3)) + +a >>>= 1; +>a : Symbol(a, Decl(numericLiteralTypes4.ts, 0, 3)) + +a <<= 1; +>a : Symbol(a, Decl(numericLiteralTypes4.ts, 0, 3)) + +b ++; +>b : Symbol(b, Decl(numericLiteralTypes4.ts, 1, 3)) + +b --; +>b : Symbol(b, Decl(numericLiteralTypes4.ts, 1, 3)) + +b += 1; +>b : Symbol(b, Decl(numericLiteralTypes4.ts, 1, 3)) + +b -= 1; +>b : Symbol(b, Decl(numericLiteralTypes4.ts, 1, 3)) + +b *= 1; +>b : Symbol(b, Decl(numericLiteralTypes4.ts, 1, 3)) + +b /= 1; +>b : Symbol(b, Decl(numericLiteralTypes4.ts, 1, 3)) + +b %= 1; +>b : Symbol(b, Decl(numericLiteralTypes4.ts, 1, 3)) + +b &= 1; +>b : Symbol(b, Decl(numericLiteralTypes4.ts, 1, 3)) + +b |= 1; +>b : Symbol(b, Decl(numericLiteralTypes4.ts, 1, 3)) + +b ^= 1; +>b : Symbol(b, Decl(numericLiteralTypes4.ts, 1, 3)) + +b >>= 1; +>b : Symbol(b, Decl(numericLiteralTypes4.ts, 1, 3)) + +b >>>= 1; +>b : Symbol(b, Decl(numericLiteralTypes4.ts, 1, 3)) + +b <<= 1; +>b : Symbol(b, Decl(numericLiteralTypes4.ts, 1, 3)) + +c ++; +>c : Symbol(c, Decl(numericLiteralTypes4.ts, 2, 3)) + +c --; +>c : Symbol(c, Decl(numericLiteralTypes4.ts, 2, 3)) + +c += 1; +>c : Symbol(c, Decl(numericLiteralTypes4.ts, 2, 3)) + +c -= 1; +>c : Symbol(c, Decl(numericLiteralTypes4.ts, 2, 3)) + +c *= 1; +>c : Symbol(c, Decl(numericLiteralTypes4.ts, 2, 3)) + +c /= 1; +>c : Symbol(c, Decl(numericLiteralTypes4.ts, 2, 3)) + +c %= 1; +>c : Symbol(c, Decl(numericLiteralTypes4.ts, 2, 3)) + +c &= 1; +>c : Symbol(c, Decl(numericLiteralTypes4.ts, 2, 3)) + +c |= 1; +>c : Symbol(c, Decl(numericLiteralTypes4.ts, 2, 3)) + +c ^= 1; +>c : Symbol(c, Decl(numericLiteralTypes4.ts, 2, 3)) + +c >>= 1; +>c : Symbol(c, Decl(numericLiteralTypes4.ts, 2, 3)) + +c >>>= 1; +>c : Symbol(c, Decl(numericLiteralTypes4.ts, 2, 3)) + +c <<= 1; +>c : Symbol(c, Decl(numericLiteralTypes4.ts, 2, 3)) + diff --git a/tests/baselines/reference/numericLiteralTypes4.types b/tests/baselines/reference/numericLiteralTypes4.types new file mode 100644 index 0000000000000..cb79dcbb4366c --- /dev/null +++ b/tests/baselines/reference/numericLiteralTypes4.types @@ -0,0 +1,202 @@ +=== tests/cases/conformance/types/literal/numericLiteralTypes4.ts === +var a: 10 = 10; +>a : 10 +>10 : 10 + +var b: 10 | 11 = 11; +>b : 10 | 11 +>11 : 11 + +var c: 10 | 11 | 12 = 10; +>c : 10 | 11 | 12 +>10 : 10 + +a ++; +>a ++ : number +>a : number + +a --; +>a -- : number +>a : number + +a += 1; +>a += 1 : number +>a : number +>1 : 1 + +a -= 1; +>a -= 1 : number +>a : number +>1 : 1 + +a *= 1; +>a *= 1 : number +>a : number +>1 : 1 + +a /= 1; +>a /= 1 : number +>a : number +>1 : 1 + +a %= 1; +>a %= 1 : number +>a : number +>1 : 1 + +a &= 1; +>a &= 1 : number +>a : number +>1 : 1 + +a |= 1; +>a |= 1 : number +>a : number +>1 : 1 + +a ^= 1; +>a ^= 1 : number +>a : number +>1 : 1 + +a >>= 1; +>a >>= 1 : number +>a : number +>1 : 1 + +a >>>= 1; +>a >>>= 1 : number +>a : number +>1 : 1 + +a <<= 1; +>a <<= 1 : number +>a : number +>1 : 1 + +b ++; +>b ++ : number +>b : number + +b --; +>b -- : number +>b : number + +b += 1; +>b += 1 : number +>b : number +>1 : 1 + +b -= 1; +>b -= 1 : number +>b : number +>1 : 1 + +b *= 1; +>b *= 1 : number +>b : number +>1 : 1 + +b /= 1; +>b /= 1 : number +>b : number +>1 : 1 + +b %= 1; +>b %= 1 : number +>b : number +>1 : 1 + +b &= 1; +>b &= 1 : number +>b : number +>1 : 1 + +b |= 1; +>b |= 1 : number +>b : number +>1 : 1 + +b ^= 1; +>b ^= 1 : number +>b : number +>1 : 1 + +b >>= 1; +>b >>= 1 : number +>b : number +>1 : 1 + +b >>>= 1; +>b >>>= 1 : number +>b : number +>1 : 1 + +b <<= 1; +>b <<= 1 : number +>b : number +>1 : 1 + +c ++; +>c ++ : number +>c : number + +c --; +>c -- : number +>c : number + +c += 1; +>c += 1 : number +>c : number +>1 : 1 + +c -= 1; +>c -= 1 : number +>c : number +>1 : 1 + +c *= 1; +>c *= 1 : number +>c : number +>1 : 1 + +c /= 1; +>c /= 1 : number +>c : number +>1 : 1 + +c %= 1; +>c %= 1 : number +>c : number +>1 : 1 + +c &= 1; +>c &= 1 : number +>c : number +>1 : 1 + +c |= 1; +>c |= 1 : number +>c : number +>1 : 1 + +c ^= 1; +>c ^= 1 : number +>c : number +>1 : 1 + +c >>= 1; +>c >>= 1 : number +>c : number +>1 : 1 + +c >>>= 1; +>c >>>= 1 : number +>c : number +>1 : 1 + +c <<= 1; +>c <<= 1 : number +>c : number +>1 : 1 + diff --git a/tests/baselines/reference/stringLiteralTypes4.errors.txt b/tests/baselines/reference/stringLiteralTypes4.errors.txt new file mode 100644 index 0000000000000..224e43c107eed --- /dev/null +++ b/tests/baselines/reference/stringLiteralTypes4.errors.txt @@ -0,0 +1,8 @@ +tests/cases/conformance/types/literal/stringLiteralTypes4.ts(2,1): error TS2736: The literal type '"foo" | "bar"' cannot be modified. + + +==== tests/cases/conformance/types/literal/stringLiteralTypes4.ts (1 errors) ==== + var s: 'foo' | 'bar' = 'bar'; + s += 'bar'; + ~ +!!! error TS2736: The literal type '"foo" | "bar"' cannot be modified. \ No newline at end of file diff --git a/tests/baselines/reference/stringLiteralTypes4.js b/tests/baselines/reference/stringLiteralTypes4.js new file mode 100644 index 0000000000000..2711ae303d618 --- /dev/null +++ b/tests/baselines/reference/stringLiteralTypes4.js @@ -0,0 +1,7 @@ +//// [stringLiteralTypes4.ts] +var s: 'foo' | 'bar' = 'bar'; +s += 'bar'; + +//// [stringLiteralTypes4.js] +var s = 'bar'; +s += 'bar'; diff --git a/tests/baselines/reference/stringLiteralTypes4.symbols b/tests/baselines/reference/stringLiteralTypes4.symbols new file mode 100644 index 0000000000000..dcab7e0b76e63 --- /dev/null +++ b/tests/baselines/reference/stringLiteralTypes4.symbols @@ -0,0 +1,7 @@ +=== tests/cases/conformance/types/literal/stringLiteralTypes4.ts === +var s: 'foo' | 'bar' = 'bar'; +>s : Symbol(s, Decl(stringLiteralTypes4.ts, 0, 3)) + +s += 'bar'; +>s : Symbol(s, Decl(stringLiteralTypes4.ts, 0, 3)) + diff --git a/tests/baselines/reference/stringLiteralTypes4.types b/tests/baselines/reference/stringLiteralTypes4.types new file mode 100644 index 0000000000000..0264cea747ddc --- /dev/null +++ b/tests/baselines/reference/stringLiteralTypes4.types @@ -0,0 +1,10 @@ +=== tests/cases/conformance/types/literal/stringLiteralTypes4.ts === +var s: 'foo' | 'bar' = 'bar'; +>s : "foo" | "bar" +>'bar' : "bar" + +s += 'bar'; +>s += 'bar' : string +>s : string +>'bar' : "bar" + diff --git a/tests/cases/conformance/types/literal/numericLiteralTypes4.ts b/tests/cases/conformance/types/literal/numericLiteralTypes4.ts new file mode 100644 index 0000000000000..05a317591ebd7 --- /dev/null +++ b/tests/cases/conformance/types/literal/numericLiteralTypes4.ts @@ -0,0 +1,45 @@ +var a: 10 = 10; +var b: 10 | 11 = 11; +var c: 10 | 11 | 12 = 10; + +a ++; +a --; +a += 1; +a -= 1; +a *= 1; +a /= 1; +a %= 1; +a &= 1; +a |= 1; +a ^= 1; +a >>= 1; +a >>>= 1; +a <<= 1; + +b ++; +b --; +b += 1; +b -= 1; +b *= 1; +b /= 1; +b %= 1; +b &= 1; +b |= 1; +b ^= 1; +b >>= 1; +b >>>= 1; +b <<= 1; + +c ++; +c --; +c += 1; +c -= 1; +c *= 1; +c /= 1; +c %= 1; +c &= 1; +c |= 1; +c ^= 1; +c >>= 1; +c >>>= 1; +c <<= 1; \ No newline at end of file diff --git a/tests/cases/conformance/types/literal/stringLiteralTypes4.ts b/tests/cases/conformance/types/literal/stringLiteralTypes4.ts new file mode 100644 index 0000000000000..e42eede5e4857 --- /dev/null +++ b/tests/cases/conformance/types/literal/stringLiteralTypes4.ts @@ -0,0 +1,2 @@ +var s: 'foo' | 'bar' = 'bar'; +s += 'bar'; \ No newline at end of file From f235b374b87c5f7a6a6a6a356bc7a9b6ef98f984 Mon Sep 17 00:00:00 2001 From: Collins Abitekaniza Date: Tue, 6 Nov 2018 20:39:23 +0300 Subject: [PATCH 3/5] check mutation for object properties --- src/compiler/checker.ts | 6 ++++-- 1 file changed, 4 insertions(+), 2 deletions(-) diff --git a/src/compiler/checker.ts b/src/compiler/checker.ts index 9e19b92677ff6..86aeb84285612 100644 --- a/src/compiler/checker.ts +++ b/src/compiler/checker.ts @@ -21804,7 +21804,8 @@ namespace ts { function checkPostfixUnaryExpression(node: PostfixUnaryExpression): Type { let operandType: Type; - const symbol = (node.operand).escapedText ? getResolvedSymbol(node.operand as Identifier) : undefined; + const symbol = isEntityNameExpression(node.operand) ? isPropertyAccessEntityNameExpression(node.operand) ? + getSymbolAtLocation((node.operand).name) : getResolvedSymbol(node.operand as Identifier) : undefined; if (symbol && !(getDeclarationNodeFlagsFromSymbol(symbol) & NodeFlags.Const)) { operandType = getTypeOfSymbol(symbol); if (isLiteralType(operandType) && !(operandType.flags & (TypeFlags.EnumLike | TypeFlags.BooleanLike | TypeFlags.Undefined))) { @@ -22181,7 +22182,8 @@ namespace ts { const operator = operatorToken.kind; let leftType: Type; - const symbol = (left).escapedText ? getResolvedSymbol(left as Identifier) : undefined; + const symbol = isEntityNameExpression(left) ? isPropertyAccessEntityNameExpression(left) ? + getSymbolAtLocation((left).name) : getResolvedSymbol(left as Identifier) : undefined; if (symbol && isCompoundAssignmentOperator(operator) && !(getDeclarationNodeFlagsFromSymbol(symbol) & NodeFlags.Const)) { leftType = getTypeOfSymbol(getResolvedSymbol(left as Identifier)); if (isLiteralType(leftType) && !(leftType.flags & (TypeFlags.EnumLike | TypeFlags.BooleanLike | TypeFlags.Undefined))) { From 1512028279f4f99de48ded5c8a9cd40e3fbf6a9a Mon Sep 17 00:00:00 2001 From: Collins Abitekaniza Date: Tue, 6 Nov 2018 23:52:19 +0300 Subject: [PATCH 4/5] check both prefix + postfix unary expressions --- src/compiler/checker.ts | 37 +++++++++++++++++++++++-------------- src/compiler/utilities.ts | 6 ++++++ 2 files changed, 29 insertions(+), 14 deletions(-) diff --git a/src/compiler/checker.ts b/src/compiler/checker.ts index 86aeb84285612..06ee17946fbf3 100644 --- a/src/compiler/checker.ts +++ b/src/compiler/checker.ts @@ -13268,6 +13268,11 @@ namespace ts { isUnitType(type); } + function isStringOrNumericLiteralType(type: Type): boolean { + return type.flags & TypeFlags.Union ? every((type).types, t => !!(t.flags & TypeFlags.StringOrNumberLiteral && !(t.flags & (TypeFlags.EnumLike | TypeFlags.Intrinsic)))) : + !!(type.flags & TypeFlags.StringOrNumberLiteral) && !(type.flags & (TypeFlags.EnumLike | TypeFlags.Intrinsic)) + } + function getBaseTypeOfLiteralType(type: Type): Type { return type.flags & TypeFlags.EnumLiteral ? getBaseTypeOfEnumLiteralType(type) : type.flags & TypeFlags.StringLiteral ? stringType : @@ -21803,17 +21808,7 @@ namespace ts { } function checkPostfixUnaryExpression(node: PostfixUnaryExpression): Type { - let operandType: Type; - const symbol = isEntityNameExpression(node.operand) ? isPropertyAccessEntityNameExpression(node.operand) ? - getSymbolAtLocation((node.operand).name) : getResolvedSymbol(node.operand as Identifier) : undefined; - if (symbol && !(getDeclarationNodeFlagsFromSymbol(symbol) & NodeFlags.Const)) { - operandType = getTypeOfSymbol(symbol); - if (isLiteralType(operandType) && !(operandType.flags & (TypeFlags.EnumLike | TypeFlags.BooleanLike | TypeFlags.Undefined))) { - error(node.operand, Diagnostics.The_literal_type_0_cannot_be_modified, typeToString(operandType)); - } - } - operandType = checkExpression(node.operand); - + const operandType = checkExpression(node.operand); if (operandType === silentNeverType) { return silentNeverType; } @@ -21838,6 +21833,21 @@ namespace ts { return numberType; } + function checkUnaryExpression(node: PrefixUnaryExpression | PostfixUnaryExpression): Type { + const symbol = isEntityNameExpression(node.operand) ? isPropertyAccessEntityNameExpression(node.operand) ? + getSymbolAtLocation((node.operand).name) : getResolvedSymbol(node.operand as Identifier) : undefined; + if (symbol && isUnaryAssignmentOperator(node.operator) && !(getDeclarationNodeFlagsFromSymbol(symbol) & NodeFlags.Const)) { + const operandType = getTypeOfSymbol(symbol); + if (isStringOrNumericLiteralType(operandType)) { + error(node.operand, Diagnostics.The_literal_type_0_cannot_be_modified, typeToString(operandType)); + } + } + if (node.kind == SyntaxKind.PrefixUnaryExpression) { + return checkPrefixUnaryExpression(node) + } + return checkPostfixUnaryExpression(node) + } + // Return true if type might be of the given kind. A union or intersection type might be of a given // kind if at least one constituent type is of the given kind. function maybeTypeOfKind(type: Type, kind: TypeFlags): boolean { @@ -22186,7 +22196,7 @@ namespace ts { getSymbolAtLocation((left).name) : getResolvedSymbol(left as Identifier) : undefined; if (symbol && isCompoundAssignmentOperator(operator) && !(getDeclarationNodeFlagsFromSymbol(symbol) & NodeFlags.Const)) { leftType = getTypeOfSymbol(getResolvedSymbol(left as Identifier)); - if (isLiteralType(leftType) && !(leftType.flags & (TypeFlags.EnumLike | TypeFlags.BooleanLike | TypeFlags.Undefined))) { + if (isStringOrNumericLiteralType(leftType)) { error(left, Diagnostics.The_literal_type_0_cannot_be_modified, typeToString(leftType)); } } @@ -22885,9 +22895,8 @@ namespace ts { case SyntaxKind.AwaitExpression: return checkAwaitExpression(node); case SyntaxKind.PrefixUnaryExpression: - return checkPrefixUnaryExpression(node); case SyntaxKind.PostfixUnaryExpression: - return checkPostfixUnaryExpression(node); + return checkUnaryExpression(node); case SyntaxKind.BinaryExpression: return checkBinaryExpression(node, checkMode); case SyntaxKind.ConditionalExpression: diff --git a/src/compiler/utilities.ts b/src/compiler/utilities.ts index dd2e7eae5b36c..78df400ef9685 100644 --- a/src/compiler/utilities.ts +++ b/src/compiler/utilities.ts @@ -3854,6 +3854,12 @@ namespace ts { || token === SyntaxKind.GreaterThanGreaterThanEqualsToken; } + export function isUnaryAssignmentOperator(token: SyntaxKind): boolean { + return token === SyntaxKind.PlusPlusToken + || token === SyntaxKind.MinusMinusToken + + } + export function isAssignmentOperator(token: SyntaxKind): boolean { return token >= SyntaxKind.FirstAssignment && token <= SyntaxKind.LastAssignment; } From ddc9c165d8081e1a6d66d146ec8383ffaac86076 Mon Sep 17 00:00:00 2001 From: Collins Abitekaniza Date: Wed, 7 Nov 2018 00:16:48 +0300 Subject: [PATCH 5/5] add more baseline tests + refactor --- src/compiler/checker.ts | 12 +- src/compiler/utilities.ts | 2 +- .../reference/enumLiteralTypes1.errors.txt | 119 ----------- .../reference/literalTypeProperty.errors.txt | 58 ++++++ .../reference/literalTypeProperty.js | 35 ++++ .../reference/literalTypeProperty.symbols | 75 +++++++ .../reference/literalTypeProperty.types | 92 +++++++++ .../reference/numericLiteralTypes1.errors.txt | 8 +- .../reference/numericLiteralTypes2.errors.txt | 8 +- .../reference/numericLiteralTypes4.errors.txt | 185 ++++++++++-------- .../reference/numericLiteralTypes4.js | 17 +- .../reference/numericLiteralTypes4.symbols | 18 ++ .../reference/numericLiteralTypes4.types | 24 +++ .../reference/stringLiteralTypes4.errors.txt | 4 +- .../types/literal/literalTypeProperty.ts | 19 ++ .../types/literal/numericLiteralTypes4.ts | 11 +- 16 files changed, 470 insertions(+), 217 deletions(-) delete mode 100644 tests/baselines/reference/enumLiteralTypes1.errors.txt create mode 100644 tests/baselines/reference/literalTypeProperty.errors.txt create mode 100644 tests/baselines/reference/literalTypeProperty.js create mode 100644 tests/baselines/reference/literalTypeProperty.symbols create mode 100644 tests/baselines/reference/literalTypeProperty.types create mode 100644 tests/cases/conformance/types/literal/literalTypeProperty.ts diff --git a/src/compiler/checker.ts b/src/compiler/checker.ts index 06ee17946fbf3..54e6d31f15d8c 100644 --- a/src/compiler/checker.ts +++ b/src/compiler/checker.ts @@ -13270,7 +13270,7 @@ namespace ts { function isStringOrNumericLiteralType(type: Type): boolean { return type.flags & TypeFlags.Union ? every((type).types, t => !!(t.flags & TypeFlags.StringOrNumberLiteral && !(t.flags & (TypeFlags.EnumLike | TypeFlags.Intrinsic)))) : - !!(type.flags & TypeFlags.StringOrNumberLiteral) && !(type.flags & (TypeFlags.EnumLike | TypeFlags.Intrinsic)) + !!(type.flags & TypeFlags.StringOrNumberLiteral) && !(type.flags & (TypeFlags.EnumLike | TypeFlags.Intrinsic)); } function getBaseTypeOfLiteralType(type: Type): Type { @@ -21835,17 +21835,17 @@ namespace ts { function checkUnaryExpression(node: PrefixUnaryExpression | PostfixUnaryExpression): Type { const symbol = isEntityNameExpression(node.operand) ? isPropertyAccessEntityNameExpression(node.operand) ? - getSymbolAtLocation((node.operand).name) : getResolvedSymbol(node.operand as Identifier) : undefined; + getSymbolAtLocation((node.operand).name) : getResolvedSymbol(node.operand) : undefined; if (symbol && isUnaryAssignmentOperator(node.operator) && !(getDeclarationNodeFlagsFromSymbol(symbol) & NodeFlags.Const)) { const operandType = getTypeOfSymbol(symbol); if (isStringOrNumericLiteralType(operandType)) { error(node.operand, Diagnostics.The_literal_type_0_cannot_be_modified, typeToString(operandType)); } } - if (node.kind == SyntaxKind.PrefixUnaryExpression) { - return checkPrefixUnaryExpression(node) + if (node.kind === SyntaxKind.PrefixUnaryExpression) { + return checkPrefixUnaryExpression(node); } - return checkPostfixUnaryExpression(node) + return checkPostfixUnaryExpression(node); } // Return true if type might be of the given kind. A union or intersection type might be of a given @@ -22193,7 +22193,7 @@ namespace ts { let leftType: Type; const symbol = isEntityNameExpression(left) ? isPropertyAccessEntityNameExpression(left) ? - getSymbolAtLocation((left).name) : getResolvedSymbol(left as Identifier) : undefined; + getSymbolAtLocation((left).name) : getResolvedSymbol(left) : undefined; if (symbol && isCompoundAssignmentOperator(operator) && !(getDeclarationNodeFlagsFromSymbol(symbol) & NodeFlags.Const)) { leftType = getTypeOfSymbol(getResolvedSymbol(left as Identifier)); if (isStringOrNumericLiteralType(leftType)) { diff --git a/src/compiler/utilities.ts b/src/compiler/utilities.ts index 78df400ef9685..6deef72db84f6 100644 --- a/src/compiler/utilities.ts +++ b/src/compiler/utilities.ts @@ -3856,7 +3856,7 @@ namespace ts { export function isUnaryAssignmentOperator(token: SyntaxKind): boolean { return token === SyntaxKind.PlusPlusToken - || token === SyntaxKind.MinusMinusToken + || token === SyntaxKind.MinusMinusToken; } diff --git a/tests/baselines/reference/enumLiteralTypes1.errors.txt b/tests/baselines/reference/enumLiteralTypes1.errors.txt deleted file mode 100644 index 804b851aff32f..0000000000000 --- a/tests/baselines/reference/enumLiteralTypes1.errors.txt +++ /dev/null @@ -1,119 +0,0 @@ -tests/cases/conformance/types/literal/enumLiteralTypes1.ts(44,5): error TS2736: The literal type 'YesNo' cannot be modified. - - -==== tests/cases/conformance/types/literal/enumLiteralTypes1.ts (1 errors) ==== - const enum Choice { Unknown, Yes, No }; - - type YesNo = Choice.Yes | Choice.No; - type NoYes = Choice.No | Choice.Yes; - type UnknownYesNo = Choice.Unknown | Choice.Yes | Choice.No; - - function f1() { - var a: YesNo; - var a: NoYes; - var a: Choice.Yes | Choice.No; - var a: Choice.No | Choice.Yes; - } - - function f2(a: YesNo, b: UnknownYesNo, c: Choice) { - b = a; - c = a; - c = b; - } - - function f3(a: Choice.Yes, b: YesNo) { - var x = a + b; - var x = a - b; - var x = a * b; - var x = a / b; - var x = a % b; - var x = a | b; - var x = a & b; - var x = a ^ b; - var x = -b; - var x = ~b; - var y = a == b; - var y = a != b; - var y = a === b; - var y = a !== b; - var y = a > b; - var y = a < b; - var y = a >= b; - var y = a <= b; - var y = !b; - } - - function f4(a: Choice.Yes, b: YesNo) { - a++; - b++; - ~ -!!! error TS2736: The literal type 'YesNo' cannot be modified. - } - - declare function g(x: Choice.Yes): string; - declare function g(x: Choice.No): boolean; - declare function g(x: Choice): number; - - function f5(a: YesNo, b: UnknownYesNo, c: Choice) { - var z1 = g(Choice.Yes); - var z2 = g(Choice.No); - var z3 = g(a); - var z4 = g(b); - var z5 = g(c); - } - - function assertNever(x: never): never { - throw new Error("Unexpected value"); - } - - function f10(x: YesNo) { - switch (x) { - case Choice.Yes: return "true"; - case Choice.No: return "false"; - } - } - - function f11(x: YesNo) { - switch (x) { - case Choice.Yes: return "true"; - case Choice.No: return "false"; - } - return assertNever(x); - } - - function f12(x: UnknownYesNo) { - if (x) { - x; - } - else { - x; - } - } - - function f13(x: UnknownYesNo) { - if (x === Choice.Yes) { - x; - } - else { - x; - } - } - - type Item = - { kind: Choice.Yes, a: string } | - { kind: Choice.No, b: string }; - - function f20(x: Item) { - switch (x.kind) { - case Choice.Yes: return x.a; - case Choice.No: return x.b; - } - } - - function f21(x: Item) { - switch (x.kind) { - case Choice.Yes: return x.a; - case Choice.No: return x.b; - } - return assertNever(x); - } \ No newline at end of file diff --git a/tests/baselines/reference/literalTypeProperty.errors.txt b/tests/baselines/reference/literalTypeProperty.errors.txt new file mode 100644 index 0000000000000..671e7e7ba05d6 --- /dev/null +++ b/tests/baselines/reference/literalTypeProperty.errors.txt @@ -0,0 +1,58 @@ +tests/cases/conformance/types/literal/literalTypeProperty.ts(7,1): error TS2743: The literal type '10' cannot be modified. +tests/cases/conformance/types/literal/literalTypeProperty.ts(8,1): error TS2743: The literal type '10' cannot be modified. +tests/cases/conformance/types/literal/literalTypeProperty.ts(9,1): error TS2743: The literal type '10' cannot be modified. +tests/cases/conformance/types/literal/literalTypeProperty.ts(10,1): error TS2743: The literal type '10' cannot be modified. +tests/cases/conformance/types/literal/literalTypeProperty.ts(11,3): error TS2743: The literal type '10' cannot be modified. +tests/cases/conformance/types/literal/literalTypeProperty.ts(12,3): error TS2743: The literal type '10' cannot be modified. +tests/cases/conformance/types/literal/literalTypeProperty.ts(14,1): error TS2743: The literal type '10 | 11' cannot be modified. +tests/cases/conformance/types/literal/literalTypeProperty.ts(15,1): error TS2743: The literal type '10 | 11' cannot be modified. +tests/cases/conformance/types/literal/literalTypeProperty.ts(16,1): error TS2743: The literal type '10 | 11' cannot be modified. +tests/cases/conformance/types/literal/literalTypeProperty.ts(17,1): error TS2743: The literal type '10 | 11' cannot be modified. +tests/cases/conformance/types/literal/literalTypeProperty.ts(18,3): error TS2743: The literal type '10 | 11' cannot be modified. +tests/cases/conformance/types/literal/literalTypeProperty.ts(19,3): error TS2743: The literal type '10 | 11' cannot be modified. + + +==== tests/cases/conformance/types/literal/literalTypeProperty.ts (12 errors) ==== + declare class C { + foo: 10; + bar: 10 | 11 + } + + var o = new C() + o.foo ++ + ~~~~~ +!!! error TS2743: The literal type '10' cannot be modified. + o.foo += 1 + ~~~~~ +!!! error TS2743: The literal type '10' cannot be modified. + o.foo -= 1 + ~~~~~ +!!! error TS2743: The literal type '10' cannot be modified. + o.foo -- + ~~~~~ +!!! error TS2743: The literal type '10' cannot be modified. + ++o.foo + ~~~~~ +!!! error TS2743: The literal type '10' cannot be modified. + --o.foo + ~~~~~ +!!! error TS2743: The literal type '10' cannot be modified. + + o.bar ++ + ~~~~~ +!!! error TS2743: The literal type '10 | 11' cannot be modified. + o.bar += 1 + ~~~~~ +!!! error TS2743: The literal type '10 | 11' cannot be modified. + o.bar -= 1 + ~~~~~ +!!! error TS2743: The literal type '10 | 11' cannot be modified. + o.bar -- + ~~~~~ +!!! error TS2743: The literal type '10 | 11' cannot be modified. + ++o.bar + ~~~~~ +!!! error TS2743: The literal type '10 | 11' cannot be modified. + --o.bar + ~~~~~ +!!! error TS2743: The literal type '10 | 11' cannot be modified. \ No newline at end of file diff --git a/tests/baselines/reference/literalTypeProperty.js b/tests/baselines/reference/literalTypeProperty.js new file mode 100644 index 0000000000000..da0c7ff09e01b --- /dev/null +++ b/tests/baselines/reference/literalTypeProperty.js @@ -0,0 +1,35 @@ +//// [literalTypeProperty.ts] +declare class C { + foo: 10; + bar: 10 | 11 +} + +var o = new C() +o.foo ++ +o.foo += 1 +o.foo -= 1 +o.foo -- +++o.foo +--o.foo + +o.bar ++ +o.bar += 1 +o.bar -= 1 +o.bar -- +++o.bar +--o.bar + +//// [literalTypeProperty.js] +var o = new C(); +o.foo++; +o.foo += 1; +o.foo -= 1; +o.foo--; +++o.foo; +--o.foo; +o.bar++; +o.bar += 1; +o.bar -= 1; +o.bar--; +++o.bar; +--o.bar; diff --git a/tests/baselines/reference/literalTypeProperty.symbols b/tests/baselines/reference/literalTypeProperty.symbols new file mode 100644 index 0000000000000..d673c4d11b76c --- /dev/null +++ b/tests/baselines/reference/literalTypeProperty.symbols @@ -0,0 +1,75 @@ +=== tests/cases/conformance/types/literal/literalTypeProperty.ts === +declare class C { +>C : Symbol(C, Decl(literalTypeProperty.ts, 0, 0)) + + foo: 10; +>foo : Symbol(C.foo, Decl(literalTypeProperty.ts, 0, 17)) + + bar: 10 | 11 +>bar : Symbol(C.bar, Decl(literalTypeProperty.ts, 1, 10)) +} + +var o = new C() +>o : Symbol(o, Decl(literalTypeProperty.ts, 5, 3)) +>C : Symbol(C, Decl(literalTypeProperty.ts, 0, 0)) + +o.foo ++ +>o.foo : Symbol(C.foo, Decl(literalTypeProperty.ts, 0, 17)) +>o : Symbol(o, Decl(literalTypeProperty.ts, 5, 3)) +>foo : Symbol(C.foo, Decl(literalTypeProperty.ts, 0, 17)) + +o.foo += 1 +>o.foo : Symbol(C.foo, Decl(literalTypeProperty.ts, 0, 17)) +>o : Symbol(o, Decl(literalTypeProperty.ts, 5, 3)) +>foo : Symbol(C.foo, Decl(literalTypeProperty.ts, 0, 17)) + +o.foo -= 1 +>o.foo : Symbol(C.foo, Decl(literalTypeProperty.ts, 0, 17)) +>o : Symbol(o, Decl(literalTypeProperty.ts, 5, 3)) +>foo : Symbol(C.foo, Decl(literalTypeProperty.ts, 0, 17)) + +o.foo -- +>o.foo : Symbol(C.foo, Decl(literalTypeProperty.ts, 0, 17)) +>o : Symbol(o, Decl(literalTypeProperty.ts, 5, 3)) +>foo : Symbol(C.foo, Decl(literalTypeProperty.ts, 0, 17)) + +++o.foo +>o.foo : Symbol(C.foo, Decl(literalTypeProperty.ts, 0, 17)) +>o : Symbol(o, Decl(literalTypeProperty.ts, 5, 3)) +>foo : Symbol(C.foo, Decl(literalTypeProperty.ts, 0, 17)) + +--o.foo +>o.foo : Symbol(C.foo, Decl(literalTypeProperty.ts, 0, 17)) +>o : Symbol(o, Decl(literalTypeProperty.ts, 5, 3)) +>foo : Symbol(C.foo, Decl(literalTypeProperty.ts, 0, 17)) + +o.bar ++ +>o.bar : Symbol(C.bar, Decl(literalTypeProperty.ts, 1, 10)) +>o : Symbol(o, Decl(literalTypeProperty.ts, 5, 3)) +>bar : Symbol(C.bar, Decl(literalTypeProperty.ts, 1, 10)) + +o.bar += 1 +>o.bar : Symbol(C.bar, Decl(literalTypeProperty.ts, 1, 10)) +>o : Symbol(o, Decl(literalTypeProperty.ts, 5, 3)) +>bar : Symbol(C.bar, Decl(literalTypeProperty.ts, 1, 10)) + +o.bar -= 1 +>o.bar : Symbol(C.bar, Decl(literalTypeProperty.ts, 1, 10)) +>o : Symbol(o, Decl(literalTypeProperty.ts, 5, 3)) +>bar : Symbol(C.bar, Decl(literalTypeProperty.ts, 1, 10)) + +o.bar -- +>o.bar : Symbol(C.bar, Decl(literalTypeProperty.ts, 1, 10)) +>o : Symbol(o, Decl(literalTypeProperty.ts, 5, 3)) +>bar : Symbol(C.bar, Decl(literalTypeProperty.ts, 1, 10)) + +++o.bar +>o.bar : Symbol(C.bar, Decl(literalTypeProperty.ts, 1, 10)) +>o : Symbol(o, Decl(literalTypeProperty.ts, 5, 3)) +>bar : Symbol(C.bar, Decl(literalTypeProperty.ts, 1, 10)) + +--o.bar +>o.bar : Symbol(C.bar, Decl(literalTypeProperty.ts, 1, 10)) +>o : Symbol(o, Decl(literalTypeProperty.ts, 5, 3)) +>bar : Symbol(C.bar, Decl(literalTypeProperty.ts, 1, 10)) + diff --git a/tests/baselines/reference/literalTypeProperty.types b/tests/baselines/reference/literalTypeProperty.types new file mode 100644 index 0000000000000..f4010d1ef3b7c --- /dev/null +++ b/tests/baselines/reference/literalTypeProperty.types @@ -0,0 +1,92 @@ +=== tests/cases/conformance/types/literal/literalTypeProperty.ts === +declare class C { +>C : C + + foo: 10; +>foo : 10 + + bar: 10 | 11 +>bar : 10 | 11 +} + +var o = new C() +>o : C +>new C() : C +>C : typeof C + +o.foo ++ +>o.foo ++ : number +>o.foo : number +>o : C +>foo : number + +o.foo += 1 +>o.foo += 1 : number +>o.foo : number +>o : C +>foo : number +>1 : 1 + +o.foo -= 1 +>o.foo -= 1 : number +>o.foo : number +>o : C +>foo : number +>1 : 1 + +o.foo -- +>o.foo -- : number +>o.foo : number +>o : C +>foo : number + +++o.foo +>++o.foo : number +>o.foo : number +>o : C +>foo : number + +--o.foo +>--o.foo : number +>o.foo : number +>o : C +>foo : number + +o.bar ++ +>o.bar ++ : number +>o.bar : number +>o : C +>bar : number + +o.bar += 1 +>o.bar += 1 : number +>o.bar : number +>o : C +>bar : number +>1 : 1 + +o.bar -= 1 +>o.bar -= 1 : number +>o.bar : number +>o : C +>bar : number +>1 : 1 + +o.bar -- +>o.bar -- : number +>o.bar : number +>o : C +>bar : number + +++o.bar +>++o.bar : number +>o.bar : number +>o : C +>bar : number + +--o.bar +>--o.bar : number +>o.bar : number +>o : C +>bar : number + diff --git a/tests/baselines/reference/numericLiteralTypes1.errors.txt b/tests/baselines/reference/numericLiteralTypes1.errors.txt index f8a02a0b5a28f..8b497cc449d8f 100644 --- a/tests/baselines/reference/numericLiteralTypes1.errors.txt +++ b/tests/baselines/reference/numericLiteralTypes1.errors.txt @@ -1,5 +1,5 @@ -tests/cases/conformance/types/literal/numericLiteralTypes1.ts(48,5): error TS2736: The literal type '1' cannot be modified. -tests/cases/conformance/types/literal/numericLiteralTypes1.ts(49,5): error TS2736: The literal type '0 | 1 | 2' cannot be modified. +tests/cases/conformance/types/literal/numericLiteralTypes1.ts(48,5): error TS2743: The literal type '1' cannot be modified. +tests/cases/conformance/types/literal/numericLiteralTypes1.ts(49,5): error TS2743: The literal type '0 | 1 | 2' cannot be modified. ==== tests/cases/conformance/types/literal/numericLiteralTypes1.ts (2 errors) ==== @@ -52,10 +52,10 @@ tests/cases/conformance/types/literal/numericLiteralTypes1.ts(49,5): error TS273 function f4(a: 1, b: 0 | 1 | 2) { a++; ~ -!!! error TS2736: The literal type '1' cannot be modified. +!!! error TS2743: The literal type '1' cannot be modified. b++; ~ -!!! error TS2736: The literal type '0 | 1 | 2' cannot be modified. +!!! error TS2743: The literal type '0 | 1 | 2' cannot be modified. } declare function g(x: 0): string; diff --git a/tests/baselines/reference/numericLiteralTypes2.errors.txt b/tests/baselines/reference/numericLiteralTypes2.errors.txt index 5e35ca42fdea4..082fb93d2f23e 100644 --- a/tests/baselines/reference/numericLiteralTypes2.errors.txt +++ b/tests/baselines/reference/numericLiteralTypes2.errors.txt @@ -1,5 +1,5 @@ -tests/cases/conformance/types/literal/numericLiteralTypes2.ts(48,5): error TS2736: The literal type '1' cannot be modified. -tests/cases/conformance/types/literal/numericLiteralTypes2.ts(49,5): error TS2736: The literal type '0 | 1 | 2' cannot be modified. +tests/cases/conformance/types/literal/numericLiteralTypes2.ts(48,5): error TS2743: The literal type '1' cannot be modified. +tests/cases/conformance/types/literal/numericLiteralTypes2.ts(49,5): error TS2743: The literal type '0 | 1 | 2' cannot be modified. ==== tests/cases/conformance/types/literal/numericLiteralTypes2.ts (2 errors) ==== @@ -52,10 +52,10 @@ tests/cases/conformance/types/literal/numericLiteralTypes2.ts(49,5): error TS273 function f4(a: 1, b: 0 | 1 | 2) { a++; ~ -!!! error TS2736: The literal type '1' cannot be modified. +!!! error TS2743: The literal type '1' cannot be modified. b++; ~ -!!! error TS2736: The literal type '0 | 1 | 2' cannot be modified. +!!! error TS2743: The literal type '0 | 1 | 2' cannot be modified. } declare function g(x: 0): string; diff --git a/tests/baselines/reference/numericLiteralTypes4.errors.txt b/tests/baselines/reference/numericLiteralTypes4.errors.txt index c2daf69198d75..2490104e6f403 100644 --- a/tests/baselines/reference/numericLiteralTypes4.errors.txt +++ b/tests/baselines/reference/numericLiteralTypes4.errors.txt @@ -1,165 +1,192 @@ -tests/cases/conformance/types/literal/numericLiteralTypes4.ts(5,1): error TS2736: The literal type '10' cannot be modified. -tests/cases/conformance/types/literal/numericLiteralTypes4.ts(6,1): error TS2736: The literal type '10' cannot be modified. -tests/cases/conformance/types/literal/numericLiteralTypes4.ts(7,1): error TS2736: The literal type '10' cannot be modified. -tests/cases/conformance/types/literal/numericLiteralTypes4.ts(8,1): error TS2736: The literal type '10' cannot be modified. -tests/cases/conformance/types/literal/numericLiteralTypes4.ts(9,1): error TS2736: The literal type '10' cannot be modified. -tests/cases/conformance/types/literal/numericLiteralTypes4.ts(10,1): error TS2736: The literal type '10' cannot be modified. -tests/cases/conformance/types/literal/numericLiteralTypes4.ts(11,1): error TS2736: The literal type '10' cannot be modified. -tests/cases/conformance/types/literal/numericLiteralTypes4.ts(12,1): error TS2736: The literal type '10' cannot be modified. -tests/cases/conformance/types/literal/numericLiteralTypes4.ts(13,1): error TS2736: The literal type '10' cannot be modified. -tests/cases/conformance/types/literal/numericLiteralTypes4.ts(14,1): error TS2736: The literal type '10' cannot be modified. -tests/cases/conformance/types/literal/numericLiteralTypes4.ts(15,1): error TS2736: The literal type '10' cannot be modified. -tests/cases/conformance/types/literal/numericLiteralTypes4.ts(16,1): error TS2736: The literal type '10' cannot be modified. -tests/cases/conformance/types/literal/numericLiteralTypes4.ts(17,1): error TS2736: The literal type '10' cannot be modified. -tests/cases/conformance/types/literal/numericLiteralTypes4.ts(19,1): error TS2736: The literal type '10 | 11' cannot be modified. -tests/cases/conformance/types/literal/numericLiteralTypes4.ts(20,1): error TS2736: The literal type '10 | 11' cannot be modified. -tests/cases/conformance/types/literal/numericLiteralTypes4.ts(21,1): error TS2736: The literal type '10 | 11' cannot be modified. -tests/cases/conformance/types/literal/numericLiteralTypes4.ts(22,1): error TS2736: The literal type '10 | 11' cannot be modified. -tests/cases/conformance/types/literal/numericLiteralTypes4.ts(23,1): error TS2736: The literal type '10 | 11' cannot be modified. -tests/cases/conformance/types/literal/numericLiteralTypes4.ts(24,1): error TS2736: The literal type '10 | 11' cannot be modified. -tests/cases/conformance/types/literal/numericLiteralTypes4.ts(25,1): error TS2736: The literal type '10 | 11' cannot be modified. -tests/cases/conformance/types/literal/numericLiteralTypes4.ts(26,1): error TS2736: The literal type '10 | 11' cannot be modified. -tests/cases/conformance/types/literal/numericLiteralTypes4.ts(27,1): error TS2736: The literal type '10 | 11' cannot be modified. -tests/cases/conformance/types/literal/numericLiteralTypes4.ts(28,1): error TS2736: The literal type '10 | 11' cannot be modified. -tests/cases/conformance/types/literal/numericLiteralTypes4.ts(29,1): error TS2736: The literal type '10 | 11' cannot be modified. -tests/cases/conformance/types/literal/numericLiteralTypes4.ts(30,1): error TS2736: The literal type '10 | 11' cannot be modified. -tests/cases/conformance/types/literal/numericLiteralTypes4.ts(31,1): error TS2736: The literal type '10 | 11' cannot be modified. -tests/cases/conformance/types/literal/numericLiteralTypes4.ts(33,1): error TS2736: The literal type '10 | 11 | 12' cannot be modified. -tests/cases/conformance/types/literal/numericLiteralTypes4.ts(34,1): error TS2736: The literal type '10 | 11 | 12' cannot be modified. -tests/cases/conformance/types/literal/numericLiteralTypes4.ts(35,1): error TS2736: The literal type '10 | 11 | 12' cannot be modified. -tests/cases/conformance/types/literal/numericLiteralTypes4.ts(36,1): error TS2736: The literal type '10 | 11 | 12' cannot be modified. -tests/cases/conformance/types/literal/numericLiteralTypes4.ts(37,1): error TS2736: The literal type '10 | 11 | 12' cannot be modified. -tests/cases/conformance/types/literal/numericLiteralTypes4.ts(38,1): error TS2736: The literal type '10 | 11 | 12' cannot be modified. -tests/cases/conformance/types/literal/numericLiteralTypes4.ts(39,1): error TS2736: The literal type '10 | 11 | 12' cannot be modified. -tests/cases/conformance/types/literal/numericLiteralTypes4.ts(40,1): error TS2736: The literal type '10 | 11 | 12' cannot be modified. -tests/cases/conformance/types/literal/numericLiteralTypes4.ts(41,1): error TS2736: The literal type '10 | 11 | 12' cannot be modified. -tests/cases/conformance/types/literal/numericLiteralTypes4.ts(42,1): error TS2736: The literal type '10 | 11 | 12' cannot be modified. -tests/cases/conformance/types/literal/numericLiteralTypes4.ts(43,1): error TS2736: The literal type '10 | 11 | 12' cannot be modified. -tests/cases/conformance/types/literal/numericLiteralTypes4.ts(44,1): error TS2736: The literal type '10 | 11 | 12' cannot be modified. -tests/cases/conformance/types/literal/numericLiteralTypes4.ts(45,1): error TS2736: The literal type '10 | 11 | 12' cannot be modified. +tests/cases/conformance/types/literal/numericLiteralTypes4.ts(5,1): error TS2743: The literal type '10' cannot be modified. +tests/cases/conformance/types/literal/numericLiteralTypes4.ts(6,1): error TS2743: The literal type '10' cannot be modified. +tests/cases/conformance/types/literal/numericLiteralTypes4.ts(7,1): error TS2743: The literal type '10' cannot be modified. +tests/cases/conformance/types/literal/numericLiteralTypes4.ts(8,1): error TS2743: The literal type '10' cannot be modified. +tests/cases/conformance/types/literal/numericLiteralTypes4.ts(9,1): error TS2743: The literal type '10' cannot be modified. +tests/cases/conformance/types/literal/numericLiteralTypes4.ts(10,1): error TS2743: The literal type '10' cannot be modified. +tests/cases/conformance/types/literal/numericLiteralTypes4.ts(11,1): error TS2743: The literal type '10' cannot be modified. +tests/cases/conformance/types/literal/numericLiteralTypes4.ts(12,1): error TS2743: The literal type '10' cannot be modified. +tests/cases/conformance/types/literal/numericLiteralTypes4.ts(13,1): error TS2743: The literal type '10' cannot be modified. +tests/cases/conformance/types/literal/numericLiteralTypes4.ts(14,1): error TS2743: The literal type '10' cannot be modified. +tests/cases/conformance/types/literal/numericLiteralTypes4.ts(15,1): error TS2743: The literal type '10' cannot be modified. +tests/cases/conformance/types/literal/numericLiteralTypes4.ts(16,1): error TS2743: The literal type '10' cannot be modified. +tests/cases/conformance/types/literal/numericLiteralTypes4.ts(17,1): error TS2743: The literal type '10' cannot be modified. +tests/cases/conformance/types/literal/numericLiteralTypes4.ts(19,3): error TS2743: The literal type '10' cannot be modified. +tests/cases/conformance/types/literal/numericLiteralTypes4.ts(20,3): error TS2743: The literal type '10' cannot be modified. +tests/cases/conformance/types/literal/numericLiteralTypes4.ts(22,1): error TS2743: The literal type '10 | 11' cannot be modified. +tests/cases/conformance/types/literal/numericLiteralTypes4.ts(23,1): error TS2743: The literal type '10 | 11' cannot be modified. +tests/cases/conformance/types/literal/numericLiteralTypes4.ts(24,1): error TS2743: The literal type '10 | 11' cannot be modified. +tests/cases/conformance/types/literal/numericLiteralTypes4.ts(25,1): error TS2743: The literal type '10 | 11' cannot be modified. +tests/cases/conformance/types/literal/numericLiteralTypes4.ts(26,1): error TS2743: The literal type '10 | 11' cannot be modified. +tests/cases/conformance/types/literal/numericLiteralTypes4.ts(27,1): error TS2743: The literal type '10 | 11' cannot be modified. +tests/cases/conformance/types/literal/numericLiteralTypes4.ts(28,1): error TS2743: The literal type '10 | 11' cannot be modified. +tests/cases/conformance/types/literal/numericLiteralTypes4.ts(29,1): error TS2743: The literal type '10 | 11' cannot be modified. +tests/cases/conformance/types/literal/numericLiteralTypes4.ts(30,1): error TS2743: The literal type '10 | 11' cannot be modified. +tests/cases/conformance/types/literal/numericLiteralTypes4.ts(31,1): error TS2743: The literal type '10 | 11' cannot be modified. +tests/cases/conformance/types/literal/numericLiteralTypes4.ts(32,1): error TS2743: The literal type '10 | 11' cannot be modified. +tests/cases/conformance/types/literal/numericLiteralTypes4.ts(33,1): error TS2743: The literal type '10 | 11' cannot be modified. +tests/cases/conformance/types/literal/numericLiteralTypes4.ts(34,1): error TS2743: The literal type '10 | 11' cannot be modified. +tests/cases/conformance/types/literal/numericLiteralTypes4.ts(36,3): error TS2743: The literal type '10 | 11' cannot be modified. +tests/cases/conformance/types/literal/numericLiteralTypes4.ts(37,3): error TS2743: The literal type '10 | 11' cannot be modified. +tests/cases/conformance/types/literal/numericLiteralTypes4.ts(39,1): error TS2743: The literal type '10 | 11 | 12' cannot be modified. +tests/cases/conformance/types/literal/numericLiteralTypes4.ts(40,1): error TS2743: The literal type '10 | 11 | 12' cannot be modified. +tests/cases/conformance/types/literal/numericLiteralTypes4.ts(41,1): error TS2743: The literal type '10 | 11 | 12' cannot be modified. +tests/cases/conformance/types/literal/numericLiteralTypes4.ts(42,1): error TS2743: The literal type '10 | 11 | 12' cannot be modified. +tests/cases/conformance/types/literal/numericLiteralTypes4.ts(43,1): error TS2743: The literal type '10 | 11 | 12' cannot be modified. +tests/cases/conformance/types/literal/numericLiteralTypes4.ts(44,1): error TS2743: The literal type '10 | 11 | 12' cannot be modified. +tests/cases/conformance/types/literal/numericLiteralTypes4.ts(45,1): error TS2743: The literal type '10 | 11 | 12' cannot be modified. +tests/cases/conformance/types/literal/numericLiteralTypes4.ts(46,1): error TS2743: The literal type '10 | 11 | 12' cannot be modified. +tests/cases/conformance/types/literal/numericLiteralTypes4.ts(47,1): error TS2743: The literal type '10 | 11 | 12' cannot be modified. +tests/cases/conformance/types/literal/numericLiteralTypes4.ts(48,1): error TS2743: The literal type '10 | 11 | 12' cannot be modified. +tests/cases/conformance/types/literal/numericLiteralTypes4.ts(49,1): error TS2743: The literal type '10 | 11 | 12' cannot be modified. +tests/cases/conformance/types/literal/numericLiteralTypes4.ts(50,1): error TS2743: The literal type '10 | 11 | 12' cannot be modified. +tests/cases/conformance/types/literal/numericLiteralTypes4.ts(51,1): error TS2743: The literal type '10 | 11 | 12' cannot be modified. +tests/cases/conformance/types/literal/numericLiteralTypes4.ts(53,3): error TS2743: The literal type '10 | 11 | 12' cannot be modified. +tests/cases/conformance/types/literal/numericLiteralTypes4.ts(54,3): error TS2743: The literal type '10 | 11 | 12' cannot be modified. -==== tests/cases/conformance/types/literal/numericLiteralTypes4.ts (39 errors) ==== +==== tests/cases/conformance/types/literal/numericLiteralTypes4.ts (45 errors) ==== var a: 10 = 10; var b: 10 | 11 = 11; var c: 10 | 11 | 12 = 10; a ++; ~ -!!! error TS2736: The literal type '10' cannot be modified. +!!! error TS2743: The literal type '10' cannot be modified. a --; ~ -!!! error TS2736: The literal type '10' cannot be modified. +!!! error TS2743: The literal type '10' cannot be modified. a += 1; ~ -!!! error TS2736: The literal type '10' cannot be modified. +!!! error TS2743: The literal type '10' cannot be modified. a -= 1; ~ -!!! error TS2736: The literal type '10' cannot be modified. +!!! error TS2743: The literal type '10' cannot be modified. a *= 1; ~ -!!! error TS2736: The literal type '10' cannot be modified. +!!! error TS2743: The literal type '10' cannot be modified. a /= 1; ~ -!!! error TS2736: The literal type '10' cannot be modified. +!!! error TS2743: The literal type '10' cannot be modified. a %= 1; ~ -!!! error TS2736: The literal type '10' cannot be modified. +!!! error TS2743: The literal type '10' cannot be modified. a &= 1; ~ -!!! error TS2736: The literal type '10' cannot be modified. +!!! error TS2743: The literal type '10' cannot be modified. a |= 1; ~ -!!! error TS2736: The literal type '10' cannot be modified. +!!! error TS2743: The literal type '10' cannot be modified. a ^= 1; ~ -!!! error TS2736: The literal type '10' cannot be modified. +!!! error TS2743: The literal type '10' cannot be modified. a >>= 1; ~ -!!! error TS2736: The literal type '10' cannot be modified. +!!! error TS2743: The literal type '10' cannot be modified. a >>>= 1; ~ -!!! error TS2736: The literal type '10' cannot be modified. +!!! error TS2743: The literal type '10' cannot be modified. a <<= 1; ~ -!!! error TS2736: The literal type '10' cannot be modified. +!!! error TS2743: The literal type '10' cannot be modified. + + ++a + ~ +!!! error TS2743: The literal type '10' cannot be modified. + --a + ~ +!!! error TS2743: The literal type '10' cannot be modified. b ++; ~ -!!! error TS2736: The literal type '10 | 11' cannot be modified. +!!! error TS2743: The literal type '10 | 11' cannot be modified. b --; ~ -!!! error TS2736: The literal type '10 | 11' cannot be modified. +!!! error TS2743: The literal type '10 | 11' cannot be modified. b += 1; ~ -!!! error TS2736: The literal type '10 | 11' cannot be modified. +!!! error TS2743: The literal type '10 | 11' cannot be modified. b -= 1; ~ -!!! error TS2736: The literal type '10 | 11' cannot be modified. +!!! error TS2743: The literal type '10 | 11' cannot be modified. b *= 1; ~ -!!! error TS2736: The literal type '10 | 11' cannot be modified. +!!! error TS2743: The literal type '10 | 11' cannot be modified. b /= 1; ~ -!!! error TS2736: The literal type '10 | 11' cannot be modified. +!!! error TS2743: The literal type '10 | 11' cannot be modified. b %= 1; ~ -!!! error TS2736: The literal type '10 | 11' cannot be modified. +!!! error TS2743: The literal type '10 | 11' cannot be modified. b &= 1; ~ -!!! error TS2736: The literal type '10 | 11' cannot be modified. +!!! error TS2743: The literal type '10 | 11' cannot be modified. b |= 1; ~ -!!! error TS2736: The literal type '10 | 11' cannot be modified. +!!! error TS2743: The literal type '10 | 11' cannot be modified. b ^= 1; ~ -!!! error TS2736: The literal type '10 | 11' cannot be modified. +!!! error TS2743: The literal type '10 | 11' cannot be modified. b >>= 1; ~ -!!! error TS2736: The literal type '10 | 11' cannot be modified. +!!! error TS2743: The literal type '10 | 11' cannot be modified. b >>>= 1; ~ -!!! error TS2736: The literal type '10 | 11' cannot be modified. +!!! error TS2743: The literal type '10 | 11' cannot be modified. b <<= 1; ~ -!!! error TS2736: The literal type '10 | 11' cannot be modified. +!!! error TS2743: The literal type '10 | 11' cannot be modified. + + ++b + ~ +!!! error TS2743: The literal type '10 | 11' cannot be modified. + --b + ~ +!!! error TS2743: The literal type '10 | 11' cannot be modified. c ++; ~ -!!! error TS2736: The literal type '10 | 11 | 12' cannot be modified. +!!! error TS2743: The literal type '10 | 11 | 12' cannot be modified. c --; ~ -!!! error TS2736: The literal type '10 | 11 | 12' cannot be modified. +!!! error TS2743: The literal type '10 | 11 | 12' cannot be modified. c += 1; ~ -!!! error TS2736: The literal type '10 | 11 | 12' cannot be modified. +!!! error TS2743: The literal type '10 | 11 | 12' cannot be modified. c -= 1; ~ -!!! error TS2736: The literal type '10 | 11 | 12' cannot be modified. +!!! error TS2743: The literal type '10 | 11 | 12' cannot be modified. c *= 1; ~ -!!! error TS2736: The literal type '10 | 11 | 12' cannot be modified. +!!! error TS2743: The literal type '10 | 11 | 12' cannot be modified. c /= 1; ~ -!!! error TS2736: The literal type '10 | 11 | 12' cannot be modified. +!!! error TS2743: The literal type '10 | 11 | 12' cannot be modified. c %= 1; ~ -!!! error TS2736: The literal type '10 | 11 | 12' cannot be modified. +!!! error TS2743: The literal type '10 | 11 | 12' cannot be modified. c &= 1; ~ -!!! error TS2736: The literal type '10 | 11 | 12' cannot be modified. +!!! error TS2743: The literal type '10 | 11 | 12' cannot be modified. c |= 1; ~ -!!! error TS2736: The literal type '10 | 11 | 12' cannot be modified. +!!! error TS2743: The literal type '10 | 11 | 12' cannot be modified. c ^= 1; ~ -!!! error TS2736: The literal type '10 | 11 | 12' cannot be modified. +!!! error TS2743: The literal type '10 | 11 | 12' cannot be modified. c >>= 1; ~ -!!! error TS2736: The literal type '10 | 11 | 12' cannot be modified. +!!! error TS2743: The literal type '10 | 11 | 12' cannot be modified. c >>>= 1; ~ -!!! error TS2736: The literal type '10 | 11 | 12' cannot be modified. +!!! error TS2743: The literal type '10 | 11 | 12' cannot be modified. c <<= 1; ~ -!!! error TS2736: The literal type '10 | 11 | 12' cannot be modified. \ No newline at end of file +!!! error TS2743: The literal type '10 | 11 | 12' cannot be modified. + + ++c + ~ +!!! error TS2743: The literal type '10 | 11 | 12' cannot be modified. + --c + ~ +!!! error TS2743: The literal type '10 | 11 | 12' cannot be modified. \ No newline at end of file diff --git a/tests/baselines/reference/numericLiteralTypes4.js b/tests/baselines/reference/numericLiteralTypes4.js index 0fc979a832fbe..9905ba84b7213 100644 --- a/tests/baselines/reference/numericLiteralTypes4.js +++ b/tests/baselines/reference/numericLiteralTypes4.js @@ -17,6 +17,9 @@ a >>= 1; a >>>= 1; a <<= 1; +++a +--a + b ++; b --; b += 1; @@ -31,6 +34,9 @@ b >>= 1; b >>>= 1; b <<= 1; +++b +--b + c ++; c --; c += 1; @@ -43,7 +49,10 @@ c |= 1; c ^= 1; c >>= 1; c >>>= 1; -c <<= 1; +c <<= 1; + +++c +--c //// [numericLiteralTypes4.js] var a = 10; @@ -62,6 +71,8 @@ a ^= 1; a >>= 1; a >>>= 1; a <<= 1; +++a; +--a; b++; b--; b += 1; @@ -75,6 +86,8 @@ b ^= 1; b >>= 1; b >>>= 1; b <<= 1; +++b; +--b; c++; c--; c += 1; @@ -88,3 +101,5 @@ c ^= 1; c >>= 1; c >>>= 1; c <<= 1; +++c; +--c; diff --git a/tests/baselines/reference/numericLiteralTypes4.symbols b/tests/baselines/reference/numericLiteralTypes4.symbols index 4d9705b0f0207..5a3fc674ab44b 100644 --- a/tests/baselines/reference/numericLiteralTypes4.symbols +++ b/tests/baselines/reference/numericLiteralTypes4.symbols @@ -47,6 +47,12 @@ a >>>= 1; a <<= 1; >a : Symbol(a, Decl(numericLiteralTypes4.ts, 0, 3)) +++a +>a : Symbol(a, Decl(numericLiteralTypes4.ts, 0, 3)) + +--a +>a : Symbol(a, Decl(numericLiteralTypes4.ts, 0, 3)) + b ++; >b : Symbol(b, Decl(numericLiteralTypes4.ts, 1, 3)) @@ -86,6 +92,12 @@ b >>>= 1; b <<= 1; >b : Symbol(b, Decl(numericLiteralTypes4.ts, 1, 3)) +++b +>b : Symbol(b, Decl(numericLiteralTypes4.ts, 1, 3)) + +--b +>b : Symbol(b, Decl(numericLiteralTypes4.ts, 1, 3)) + c ++; >c : Symbol(c, Decl(numericLiteralTypes4.ts, 2, 3)) @@ -125,3 +137,9 @@ c >>>= 1; c <<= 1; >c : Symbol(c, Decl(numericLiteralTypes4.ts, 2, 3)) +++c +>c : Symbol(c, Decl(numericLiteralTypes4.ts, 2, 3)) + +--c +>c : Symbol(c, Decl(numericLiteralTypes4.ts, 2, 3)) + diff --git a/tests/baselines/reference/numericLiteralTypes4.types b/tests/baselines/reference/numericLiteralTypes4.types index cb79dcbb4366c..45a76e2d73a3c 100644 --- a/tests/baselines/reference/numericLiteralTypes4.types +++ b/tests/baselines/reference/numericLiteralTypes4.types @@ -74,6 +74,14 @@ a <<= 1; >a : number >1 : 1 +++a +>++a : number +>a : number + +--a +>--a : number +>a : number + b ++; >b ++ : number >b : number @@ -137,6 +145,14 @@ b <<= 1; >b : number >1 : 1 +++b +>++b : number +>b : number + +--b +>--b : number +>b : number + c ++; >c ++ : number >c : number @@ -200,3 +216,11 @@ c <<= 1; >c : number >1 : 1 +++c +>++c : number +>c : number + +--c +>--c : number +>c : number + diff --git a/tests/baselines/reference/stringLiteralTypes4.errors.txt b/tests/baselines/reference/stringLiteralTypes4.errors.txt index 224e43c107eed..21b24a7e0b6a7 100644 --- a/tests/baselines/reference/stringLiteralTypes4.errors.txt +++ b/tests/baselines/reference/stringLiteralTypes4.errors.txt @@ -1,8 +1,8 @@ -tests/cases/conformance/types/literal/stringLiteralTypes4.ts(2,1): error TS2736: The literal type '"foo" | "bar"' cannot be modified. +tests/cases/conformance/types/literal/stringLiteralTypes4.ts(2,1): error TS2743: The literal type '"foo" | "bar"' cannot be modified. ==== tests/cases/conformance/types/literal/stringLiteralTypes4.ts (1 errors) ==== var s: 'foo' | 'bar' = 'bar'; s += 'bar'; ~ -!!! error TS2736: The literal type '"foo" | "bar"' cannot be modified. \ No newline at end of file +!!! error TS2743: The literal type '"foo" | "bar"' cannot be modified. \ No newline at end of file diff --git a/tests/cases/conformance/types/literal/literalTypeProperty.ts b/tests/cases/conformance/types/literal/literalTypeProperty.ts new file mode 100644 index 0000000000000..05dac682792c1 --- /dev/null +++ b/tests/cases/conformance/types/literal/literalTypeProperty.ts @@ -0,0 +1,19 @@ +declare class C { + foo: 10; + bar: 10 | 11 +} + +var o = new C() +o.foo ++ +o.foo += 1 +o.foo -= 1 +o.foo -- +++o.foo +--o.foo + +o.bar ++ +o.bar += 1 +o.bar -= 1 +o.bar -- +++o.bar +--o.bar \ No newline at end of file diff --git a/tests/cases/conformance/types/literal/numericLiteralTypes4.ts b/tests/cases/conformance/types/literal/numericLiteralTypes4.ts index 05a317591ebd7..c737907545ada 100644 --- a/tests/cases/conformance/types/literal/numericLiteralTypes4.ts +++ b/tests/cases/conformance/types/literal/numericLiteralTypes4.ts @@ -16,6 +16,9 @@ a >>= 1; a >>>= 1; a <<= 1; +++a +--a + b ++; b --; b += 1; @@ -30,6 +33,9 @@ b >>= 1; b >>>= 1; b <<= 1; +++b +--b + c ++; c --; c += 1; @@ -42,4 +48,7 @@ c |= 1; c ^= 1; c >>= 1; c >>>= 1; -c <<= 1; \ No newline at end of file +c <<= 1; + +++c +--c \ No newline at end of file