mirror of
https://github.com/dart-lang/sdk
synced 2024-09-16 01:45:06 +00:00
Abstract field support: do not allow abstract fields to be late or static.
Although these error conditions are not reported by the parser, the language grammar does not permit them, so from a customer perspective they are parser errors. Accordingly, they have been assigned ParserErrorCodes and reported by the AstBuilder, as we do for other similar errors. Change-Id: I79d0ad1dcad518981b8b649c117df326279008f7 Reviewed-on: https://dart-review.googlesource.com/c/sdk/+/157800 Commit-Queue: Paul Berry <paulberry@google.com> Reviewed-by: Konstantin Shcheglov <scheglov@google.com> Reviewed-by: Brian Wilkerson <brianwilkerson@google.com>
This commit is contained in:
parent
8405d7c8e3
commit
87f0d5d9dc
|
@ -89,6 +89,7 @@ const Code<Null> codeAbstractLateField = messageAbstractLateField;
|
|||
// DO NOT EDIT. THIS FILE IS GENERATED. SEE TOP OF FILE.
|
||||
const MessageCode messageAbstractLateField = const MessageCode(
|
||||
"AbstractLateField",
|
||||
index: 108,
|
||||
message: r"""Abstract fields cannot be late.""",
|
||||
tip: r"""Try removing the 'abstract' or 'late' keyword.""");
|
||||
|
||||
|
@ -134,6 +135,7 @@ const Code<Null> codeAbstractStaticField = messageAbstractStaticField;
|
|||
// DO NOT EDIT. THIS FILE IS GENERATED. SEE TOP OF FILE.
|
||||
const MessageCode messageAbstractStaticField = const MessageCode(
|
||||
"AbstractStaticField",
|
||||
index: 107,
|
||||
message: r"""Static fields can't be declared 'abstract'.""",
|
||||
tip: r"""Try removing the 'abstract' or 'static' keyword.""");
|
||||
|
||||
|
|
|
@ -570,6 +570,8 @@ const List<ErrorCode> errorCodeValues = [
|
|||
ManifestWarningCode.UNSUPPORTED_CHROME_OS_HARDWARE,
|
||||
ParserErrorCode.ABSTRACT_CLASS_MEMBER,
|
||||
ParserErrorCode.ABSTRACT_ENUM,
|
||||
ParserErrorCode.ABSTRACT_LATE_FIELD,
|
||||
ParserErrorCode.ABSTRACT_STATIC_FIELD,
|
||||
ParserErrorCode.ABSTRACT_STATIC_METHOD,
|
||||
ParserErrorCode.ABSTRACT_TOP_LEVEL_FUNCTION,
|
||||
ParserErrorCode.ABSTRACT_TOP_LEVEL_VARIABLE,
|
||||
|
|
|
@ -29,6 +29,10 @@ class ParserErrorCode extends ErrorCode {
|
|||
'ABSTRACT_ENUM', "Enums can't be declared to be 'abstract'.",
|
||||
correction: "Try removing the keyword 'abstract'.");
|
||||
|
||||
static const ParserErrorCode ABSTRACT_LATE_FIELD = _ABSTRACT_LATE_FIELD;
|
||||
|
||||
static const ParserErrorCode ABSTRACT_STATIC_FIELD = _ABSTRACT_STATIC_FIELD;
|
||||
|
||||
static const ParserErrorCode ABSTRACT_STATIC_METHOD = ParserErrorCode(
|
||||
'ABSTRACT_STATIC_METHOD',
|
||||
"Static methods can't be declared to be 'abstract'.",
|
||||
|
|
|
@ -114,6 +114,8 @@ final fastaAnalyzerErrorCodes = <ErrorCode>[
|
|||
_SETTER_CONSTRUCTOR,
|
||||
_MEMBER_WITH_CLASS_NAME,
|
||||
_EXTERNAL_CONSTRUCTOR_WITH_INITIALIZER,
|
||||
_ABSTRACT_STATIC_FIELD,
|
||||
_ABSTRACT_LATE_FIELD,
|
||||
];
|
||||
|
||||
const ParserErrorCode _ABSTRACT_CLASS_MEMBER = ParserErrorCode(
|
||||
|
@ -122,6 +124,14 @@ const ParserErrorCode _ABSTRACT_CLASS_MEMBER = ParserErrorCode(
|
|||
correction:
|
||||
"Try removing the 'abstract' keyword. You can add the 'abstract' keyword before the class declaration.");
|
||||
|
||||
const ParserErrorCode _ABSTRACT_LATE_FIELD = ParserErrorCode(
|
||||
'ABSTRACT_LATE_FIELD', r"Abstract fields cannot be late.",
|
||||
correction: "Try removing the 'abstract' or 'late' keyword.");
|
||||
|
||||
const ParserErrorCode _ABSTRACT_STATIC_FIELD = ParserErrorCode(
|
||||
'ABSTRACT_STATIC_FIELD', r"Static fields can't be declared 'abstract'.",
|
||||
correction: "Try removing the 'abstract' or 'static' keyword.");
|
||||
|
||||
const ParserErrorCode _ANNOTATION_WITH_TYPE_ARGUMENTS = ParserErrorCode(
|
||||
'ANNOTATION_WITH_TYPE_ARGUMENTS',
|
||||
r"An annotation (metadata) can't use type arguments.");
|
||||
|
|
|
@ -8,6 +8,8 @@ import 'package:_fe_analyzer_shared/src/messages/codes.dart'
|
|||
Message,
|
||||
MessageCode,
|
||||
messageAbstractClassMember,
|
||||
messageAbstractLateField,
|
||||
messageAbstractStaticField,
|
||||
messageConstConstructorWithBody,
|
||||
messageConstructorWithTypeParameters,
|
||||
messageDirectiveAfterDeclaration,
|
||||
|
@ -849,9 +851,20 @@ class AstBuilder extends StackListener {
|
|||
assert(optional(';', semicolon));
|
||||
debugEvent("Fields");
|
||||
|
||||
if (!enableNonNullable && abstractToken != null) {
|
||||
handleRecoverableError(
|
||||
messageAbstractClassMember, abstractToken, abstractToken);
|
||||
if (abstractToken != null) {
|
||||
if (!enableNonNullable) {
|
||||
handleRecoverableError(
|
||||
messageAbstractClassMember, abstractToken, abstractToken);
|
||||
} else {
|
||||
if (staticToken != null) {
|
||||
handleRecoverableError(
|
||||
messageAbstractStaticField, abstractToken, abstractToken);
|
||||
}
|
||||
if (lateToken != null) {
|
||||
handleRecoverableError(
|
||||
messageAbstractLateField, abstractToken, abstractToken);
|
||||
}
|
||||
}
|
||||
}
|
||||
if (externalToken != null) {
|
||||
handleRecoverableError(
|
||||
|
|
|
@ -182,6 +182,42 @@ class ClassMemberParserTest_Fasta extends FastaParserTestCase
|
|||
expect(field.abstractKeyword, isNotNull);
|
||||
}
|
||||
|
||||
void test_parseField_abstract_late() {
|
||||
createParser('abstract late int? i;', featureSet: nonNullable);
|
||||
ClassMember member = parser.parseClassMember('C');
|
||||
expect(member, isNotNull);
|
||||
assertErrors(errors: [
|
||||
expectedError(ParserErrorCode.ABSTRACT_LATE_FIELD, 0, 8),
|
||||
]);
|
||||
expect(member, isFieldDeclaration);
|
||||
FieldDeclaration field = member;
|
||||
expect(field.abstractKeyword, isNotNull);
|
||||
}
|
||||
|
||||
void test_parseField_abstract_late_final() {
|
||||
createParser('abstract late final int? i;', featureSet: nonNullable);
|
||||
ClassMember member = parser.parseClassMember('C');
|
||||
expect(member, isNotNull);
|
||||
assertErrors(errors: [
|
||||
expectedError(ParserErrorCode.ABSTRACT_LATE_FIELD, 0, 8),
|
||||
]);
|
||||
expect(member, isFieldDeclaration);
|
||||
FieldDeclaration field = member;
|
||||
expect(field.abstractKeyword, isNotNull);
|
||||
}
|
||||
|
||||
void test_parseField_abstract_static() {
|
||||
createParser('abstract static int? i;', featureSet: nonNullable);
|
||||
ClassMember member = parser.parseClassMember('C');
|
||||
expect(member, isNotNull);
|
||||
assertErrors(errors: [
|
||||
expectedError(ParserErrorCode.ABSTRACT_STATIC_FIELD, 0, 8),
|
||||
]);
|
||||
expect(member, isFieldDeclaration);
|
||||
FieldDeclaration field = member;
|
||||
expect(field.abstractKeyword, isNotNull);
|
||||
}
|
||||
|
||||
void test_parseField_const_late() {
|
||||
createParser('const late T f = 0;', featureSet: nonNullable);
|
||||
ClassMember member = parser.parseClassMember('C');
|
||||
|
|
|
@ -11,10 +11,8 @@ AbstractFieldInitializer/analyzerCode: Fail
|
|||
AbstractExtensionField/analyzerCode: Fail
|
||||
AbstractExtensionField/example: Fail
|
||||
AbstractExternalField/analyzerCode: Fail
|
||||
AbstractLateField/analyzerCode: Fail
|
||||
AbstractNotSync/example: Fail
|
||||
AbstractRedirectedClassInstantiation/example: Fail
|
||||
AbstractStaticField/analyzerCode: Fail
|
||||
AccessError/analyzerCode: Fail
|
||||
AccessError/example: Fail
|
||||
AmbiguousExtensionMethod/analyzerCode: Fail
|
||||
|
|
|
@ -563,7 +563,9 @@ AbstractExternalField:
|
|||
- "abstract class C {external abstract var f;}"
|
||||
|
||||
AbstractStaticField:
|
||||
index: 107
|
||||
template: "Static fields can't be declared 'abstract'."
|
||||
analyzerCode: ParserErrorCode.ABSTRACT_STATIC_FIELD
|
||||
tip: "Try removing the 'abstract' or 'static' keyword."
|
||||
configuration: nnbd-strong
|
||||
script:
|
||||
|
@ -593,7 +595,9 @@ AbstractFieldConstructorInitializer:
|
|||
- "abstract class C {abstract var f; C() : this.f = 0;}"
|
||||
|
||||
AbstractLateField:
|
||||
index: 108
|
||||
template: "Abstract fields cannot be late."
|
||||
analyzerCode: ParserErrorCode.ABSTRACT_LATE_FIELD
|
||||
tip: "Try removing the 'abstract' or 'late' keyword."
|
||||
configuration: nnbd-strong
|
||||
script:
|
||||
|
|
Loading…
Reference in a new issue