From 4a59b63f35f7eaa8de5721024d3c37834a0809c8 Mon Sep 17 00:00:00 2001 From: Nathan Shively-Sanders <293473+sandersn@users.noreply.github.com> Date: Thu, 20 May 2021 07:18:18 -0700 Subject: [PATCH] Error for abstract property with initialiser (#43615) * Error for abstract property with initialiser * remove stray LF * update baselines --- src/compiler/checker.ts | 7 +++++-- src/compiler/diagnosticMessages.json | 4 ++++ .../abstractPropertyInitializer.errors.txt | 10 ++++++++++ .../reference/abstractPropertyInitializer.js | 19 +++++++++++++++++++ .../abstractPropertyInitializer.symbols | 8 ++++++++ .../abstractPropertyInitializer.types | 9 +++++++++ .../accessorsOverrideProperty7.errors.txt | 5 ++++- ...ivateNamesIncompatibleModifiers.errors.txt | 5 ++++- .../abstractPropertyInitializer.ts | 5 +++++ 9 files changed, 68 insertions(+), 4 deletions(-) create mode 100644 tests/baselines/reference/abstractPropertyInitializer.errors.txt create mode 100644 tests/baselines/reference/abstractPropertyInitializer.js create mode 100644 tests/baselines/reference/abstractPropertyInitializer.symbols create mode 100644 tests/baselines/reference/abstractPropertyInitializer.types create mode 100644 tests/cases/conformance/classes/propertyMemberDeclarations/abstractPropertyInitializer.ts diff --git a/src/compiler/checker.ts b/src/compiler/checker.ts index 7834e4e313c..f4ead0ad962 100644 --- a/src/compiler/checker.ts +++ b/src/compiler/checker.ts @@ -33344,6 +33344,10 @@ namespace ts { if (isPrivateIdentifier(node.name) && hasStaticModifier(node) && node.initializer && languageVersion === ScriptTarget.ESNext && !compilerOptions.useDefineForClassFields) { error(node.initializer, Diagnostics.Static_fields_with_private_names_can_t_have_initializers_when_the_useDefineForClassFields_flag_is_not_specified_with_a_target_of_esnext_Consider_adding_the_useDefineForClassFields_flag); } + // property signatures already report "initializer not allowed in ambient context" elsewhere + if (hasSyntacticModifier(node, ModifierFlags.Abstract) && node.kind === SyntaxKind.PropertyDeclaration && node.initializer) { + error(node, Diagnostics.Property_0_cannot_have_an_initializer_because_it_is_marked_abstract, declarationNameToString(node.name)); + } } function checkPropertySignature(node: PropertySignature) { @@ -33360,8 +33364,7 @@ namespace ts { // Grammar checking for modifiers is done inside the function checkGrammarFunctionLikeDeclaration checkFunctionOrMethodDeclaration(node); - // Abstract methods cannot have an implementation. - // Extra checks are to avoid reporting multiple errors relating to the "abstractness" of the node. + // method signatures already report "implementation not allowed in ambient context" elsewhere if (hasSyntacticModifier(node, ModifierFlags.Abstract) && node.kind === SyntaxKind.MethodDeclaration && node.body) { error(node, Diagnostics.Method_0_cannot_have_an_implementation_because_it_is_marked_abstract, declarationNameToString(node.name)); } diff --git a/src/compiler/diagnosticMessages.json b/src/compiler/diagnosticMessages.json index ba749e78668..11afc95db9b 100644 --- a/src/compiler/diagnosticMessages.json +++ b/src/compiler/diagnosticMessages.json @@ -887,6 +887,10 @@ "category": "Error", "code": 1266 }, + "Property '{0}' cannot have an initializer because it is marked abstract.": { + "category": "Error", + "code": 1267 + }, "'with' statements are not allowed in an async function block.": { "category": "Error", diff --git a/tests/baselines/reference/abstractPropertyInitializer.errors.txt b/tests/baselines/reference/abstractPropertyInitializer.errors.txt new file mode 100644 index 00000000000..f9ccf2b1226 --- /dev/null +++ b/tests/baselines/reference/abstractPropertyInitializer.errors.txt @@ -0,0 +1,10 @@ +tests/cases/conformance/classes/propertyMemberDeclarations/abstractPropertyInitializer.ts(2,14): error TS1267: Property 'prop' cannot have an initializer because it is marked abstract. + + +==== tests/cases/conformance/classes/propertyMemberDeclarations/abstractPropertyInitializer.ts (1 errors) ==== + abstract class C { + abstract prop = 1 + ~~~~ +!!! error TS1267: Property 'prop' cannot have an initializer because it is marked abstract. + } + \ No newline at end of file diff --git a/tests/baselines/reference/abstractPropertyInitializer.js b/tests/baselines/reference/abstractPropertyInitializer.js new file mode 100644 index 00000000000..efd9d52a96e --- /dev/null +++ b/tests/baselines/reference/abstractPropertyInitializer.js @@ -0,0 +1,19 @@ +//// [abstractPropertyInitializer.ts] +abstract class C { + abstract prop = 1 +} + + +//// [abstractPropertyInitializer.js] +"use strict"; +var C = /** @class */ (function () { + function C() { + } + return C; +}()); + + +//// [abstractPropertyInitializer.d.ts] +declare abstract class C { + abstract prop: number; +} diff --git a/tests/baselines/reference/abstractPropertyInitializer.symbols b/tests/baselines/reference/abstractPropertyInitializer.symbols new file mode 100644 index 00000000000..f2fa37c7968 --- /dev/null +++ b/tests/baselines/reference/abstractPropertyInitializer.symbols @@ -0,0 +1,8 @@ +=== tests/cases/conformance/classes/propertyMemberDeclarations/abstractPropertyInitializer.ts === +abstract class C { +>C : Symbol(C, Decl(abstractPropertyInitializer.ts, 0, 0)) + + abstract prop = 1 +>prop : Symbol(C.prop, Decl(abstractPropertyInitializer.ts, 0, 18)) +} + diff --git a/tests/baselines/reference/abstractPropertyInitializer.types b/tests/baselines/reference/abstractPropertyInitializer.types new file mode 100644 index 00000000000..36ef0a62142 --- /dev/null +++ b/tests/baselines/reference/abstractPropertyInitializer.types @@ -0,0 +1,9 @@ +=== tests/cases/conformance/classes/propertyMemberDeclarations/abstractPropertyInitializer.ts === +abstract class C { +>C : C + + abstract prop = 1 +>prop : number +>1 : 1 +} + diff --git a/tests/baselines/reference/accessorsOverrideProperty7.errors.txt b/tests/baselines/reference/accessorsOverrideProperty7.errors.txt index 00b9a050cb4..c83e5e6295b 100644 --- a/tests/baselines/reference/accessorsOverrideProperty7.errors.txt +++ b/tests/baselines/reference/accessorsOverrideProperty7.errors.txt @@ -1,9 +1,12 @@ +tests/cases/conformance/classes/propertyMemberDeclarations/accessorsOverrideProperty7.ts(2,14): error TS1267: Property 'p' cannot have an initializer because it is marked abstract. tests/cases/conformance/classes/propertyMemberDeclarations/accessorsOverrideProperty7.ts(5,9): error TS2611: 'p' is defined as a property in class 'A', but is overridden here in 'B' as an accessor. -==== tests/cases/conformance/classes/propertyMemberDeclarations/accessorsOverrideProperty7.ts (1 errors) ==== +==== tests/cases/conformance/classes/propertyMemberDeclarations/accessorsOverrideProperty7.ts (2 errors) ==== abstract class A { abstract p = 'yep' + ~ +!!! error TS1267: Property 'p' cannot have an initializer because it is marked abstract. } class B extends A { get p() { return 'oh no' } // error diff --git a/tests/baselines/reference/privateNamesIncompatibleModifiers.errors.txt b/tests/baselines/reference/privateNamesIncompatibleModifiers.errors.txt index f1f44a3d4f1..7f6a6b9faf6 100644 --- a/tests/baselines/reference/privateNamesIncompatibleModifiers.errors.txt +++ b/tests/baselines/reference/privateNamesIncompatibleModifiers.errors.txt @@ -21,10 +21,11 @@ tests/cases/conformance/classes/members/privateNames/privateNamesIncompatibleMod tests/cases/conformance/classes/members/privateNames/privateNamesIncompatibleModifiers.ts(27,5): error TS1042: 'async' modifier cannot be used here. tests/cases/conformance/classes/members/privateNames/privateNamesIncompatibleModifiers.ts(28,5): error TS1042: 'async' modifier cannot be used here. tests/cases/conformance/classes/members/privateNames/privateNamesIncompatibleModifiers.ts(32,5): error TS18019: 'abstract' modifier cannot be used with a private identifier. +tests/cases/conformance/classes/members/privateNames/privateNamesIncompatibleModifiers.ts(32,14): error TS1267: Property '#quux' cannot have an initializer because it is marked abstract. !!! error TS2318: Cannot find global type 'AsyncIterableIterator'. -==== tests/cases/conformance/classes/members/privateNames/privateNamesIncompatibleModifiers.ts (22 errors) ==== +==== tests/cases/conformance/classes/members/privateNames/privateNamesIncompatibleModifiers.ts (23 errors) ==== class A { public #foo = 3; // Error ~~~~~~ @@ -101,5 +102,7 @@ tests/cases/conformance/classes/members/privateNames/privateNamesIncompatibleMod abstract #quux = 3; // Error ~~~~~~~~ !!! error TS18019: 'abstract' modifier cannot be used with a private identifier. + ~~~~~ +!!! error TS1267: Property '#quux' cannot have an initializer because it is marked abstract. } \ No newline at end of file diff --git a/tests/cases/conformance/classes/propertyMemberDeclarations/abstractPropertyInitializer.ts b/tests/cases/conformance/classes/propertyMemberDeclarations/abstractPropertyInitializer.ts new file mode 100644 index 00000000000..42a0999748a --- /dev/null +++ b/tests/cases/conformance/classes/propertyMemberDeclarations/abstractPropertyInitializer.ts @@ -0,0 +1,5 @@ +// @strict: true +// @declaration: true +abstract class C { + abstract prop = 1 +}