Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(24)

Unified Diff: pkg/analyzer/test/generated/resolver_test_case.dart

Issue 1843473002: Sort analyzer sources (Closed) Base URL: https://github.com/dart-lang/sdk.git@master
Patch Set: Remove generated file and fix misplaced comments Created 4 years, 9 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View side-by-side diff with in-line comments
Download patch
Index: pkg/analyzer/test/generated/resolver_test_case.dart
diff --git a/pkg/analyzer/test/generated/resolver_test_case.dart b/pkg/analyzer/test/generated/resolver_test_case.dart
index f6bd1cf9c66c8e5667c9ab1ff5f20c62191369a8..15575416b448320f96851137f41a3ba9e90ba96c 100644
--- a/pkg/analyzer/test/generated/resolver_test_case.dart
+++ b/pkg/analyzer/test/generated/resolver_test_case.dart
@@ -24,6 +24,279 @@ import 'package:unittest/unittest.dart';
import 'analysis_context_factory.dart';
import 'test_support.dart';
+/**
+ * An AST visitor used to verify that all of the nodes in an AST structure that
+ * should have been resolved were resolved.
+ */
+class ResolutionVerifier extends RecursiveAstVisitor<Object> {
+ /**
+ * A set containing nodes that are known to not be resolvable and should
+ * therefore not cause the test to fail.
+ */
+ final Set<AstNode> _knownExceptions;
+
+ /**
+ * A list containing all of the AST nodes that were not resolved.
+ */
+ List<AstNode> _unresolvedNodes = new List<AstNode>();
+
+ /**
+ * A list containing all of the AST nodes that were resolved to an element of
+ * the wrong type.
+ */
+ List<AstNode> _wrongTypedNodes = new List<AstNode>();
+
+ /**
+ * Initialize a newly created verifier to verify that all of the identifiers
+ * in the visited AST structures that are expected to have been resolved have
+ * an element associated with them. Nodes in the set of [_knownExceptions] are
+ * not expected to have been resolved, even if they normally would have been
+ * expected to have been resolved.
+ */
+ ResolutionVerifier([this._knownExceptions]);
+
+ /**
+ * Assert that all of the visited identifiers were resolved.
+ */
+ void assertResolved() {
+ if (!_unresolvedNodes.isEmpty || !_wrongTypedNodes.isEmpty) {
+ StringBuffer buffer = new StringBuffer();
+ if (!_unresolvedNodes.isEmpty) {
+ buffer.write("Failed to resolve ");
+ buffer.write(_unresolvedNodes.length);
+ buffer.writeln(" nodes:");
+ _printNodes(buffer, _unresolvedNodes);
+ }
+ if (!_wrongTypedNodes.isEmpty) {
+ buffer.write("Resolved ");
+ buffer.write(_wrongTypedNodes.length);
+ buffer.writeln(" to the wrong type of element:");
+ _printNodes(buffer, _wrongTypedNodes);
+ }
+ fail(buffer.toString());
+ }
+ }
+
+ @override
+ Object visitAnnotation(Annotation node) {
+ node.visitChildren(this);
+ ElementAnnotation elementAnnotation = node.elementAnnotation;
+ if (elementAnnotation == null) {
+ if (_knownExceptions == null || !_knownExceptions.contains(node)) {
+ _unresolvedNodes.add(node);
+ }
+ } else if (elementAnnotation is! ElementAnnotation) {
+ _wrongTypedNodes.add(node);
+ }
+ return null;
+ }
+
+ @override
+ Object visitBinaryExpression(BinaryExpression node) {
+ node.visitChildren(this);
+ if (!node.operator.isUserDefinableOperator) {
+ return null;
+ }
+ DartType operandType = node.leftOperand.staticType;
+ if (operandType == null || operandType.isDynamic) {
+ return null;
+ }
+ return _checkResolved(
+ node, node.staticElement, (node) => node is MethodElement);
+ }
+
+ @override
+ Object visitCommentReference(CommentReference node) => null;
+
+ @override
+ Object visitCompilationUnit(CompilationUnit node) {
+ node.visitChildren(this);
+ return _checkResolved(
+ node, node.element, (node) => node is CompilationUnitElement);
+ }
+
+ @override
+ Object visitExportDirective(ExportDirective node) =>
+ _checkResolved(node, node.element, (node) => node is ExportElement);
+
+ @override
+ Object visitFunctionDeclaration(FunctionDeclaration node) {
+ node.visitChildren(this);
+ if (node.element is LibraryElement) {
+ _wrongTypedNodes.add(node);
+ }
+ return null;
+ }
+
+ @override
+ Object visitFunctionExpressionInvocation(FunctionExpressionInvocation node) {
+ node.visitChildren(this);
+ // TODO(brianwilkerson) If we start resolving function expressions, then
+ // conditionally check to see whether the node was resolved correctly.
+ return null;
+ //checkResolved(node, node.getElement(), FunctionElement.class);
+ }
+
+ @override
+ Object visitImportDirective(ImportDirective node) {
+ // Not sure how to test the combinators given that it isn't an error if the
+ // names are not defined.
+ _checkResolved(node, node.element, (node) => node is ImportElement);
+ SimpleIdentifier prefix = node.prefix;
+ if (prefix == null) {
+ return null;
+ }
+ return _checkResolved(
+ prefix, prefix.staticElement, (node) => node is PrefixElement);
+ }
+
+ @override
+ Object visitIndexExpression(IndexExpression node) {
+ node.visitChildren(this);
+ DartType targetType = node.realTarget.staticType;
+ if (targetType == null || targetType.isDynamic) {
+ return null;
+ }
+ return _checkResolved(
+ node, node.staticElement, (node) => node is MethodElement);
+ }
+
+ @override
+ Object visitLibraryDirective(LibraryDirective node) =>
+ _checkResolved(node, node.element, (node) => node is LibraryElement);
+
+ @override
+ Object visitNamedExpression(NamedExpression node) =>
+ node.expression.accept(this);
+
+ @override
+ Object visitPartDirective(PartDirective node) => _checkResolved(
+ node, node.element, (node) => node is CompilationUnitElement);
+
+ @override
+ Object visitPartOfDirective(PartOfDirective node) =>
+ _checkResolved(node, node.element, (node) => node is LibraryElement);
+
+ @override
+ Object visitPostfixExpression(PostfixExpression node) {
+ node.visitChildren(this);
+ if (!node.operator.isUserDefinableOperator) {
+ return null;
+ }
+ DartType operandType = node.operand.staticType;
+ if (operandType == null || operandType.isDynamic) {
+ return null;
+ }
+ return _checkResolved(
+ node, node.staticElement, (node) => node is MethodElement);
+ }
+
+ @override
+ Object visitPrefixedIdentifier(PrefixedIdentifier node) {
+ SimpleIdentifier prefix = node.prefix;
+ prefix.accept(this);
+ DartType prefixType = prefix.staticType;
+ if (prefixType == null || prefixType.isDynamic) {
+ return null;
+ }
+ return _checkResolved(node, node.staticElement, null);
+ }
+
+ @override
+ Object visitPrefixExpression(PrefixExpression node) {
+ node.visitChildren(this);
+ if (!node.operator.isUserDefinableOperator) {
+ return null;
+ }
+ DartType operandType = node.operand.staticType;
+ if (operandType == null || operandType.isDynamic) {
+ return null;
+ }
+ return _checkResolved(
+ node, node.staticElement, (node) => node is MethodElement);
+ }
+
+ @override
+ Object visitPropertyAccess(PropertyAccess node) {
+ Expression target = node.realTarget;
+ target.accept(this);
+ DartType targetType = target.staticType;
+ if (targetType == null || targetType.isDynamic) {
+ return null;
+ }
+ return node.propertyName.accept(this);
+ }
+
+ @override
+ Object visitSimpleIdentifier(SimpleIdentifier node) {
+ if (node.name == "void") {
+ return null;
+ }
+ if (node.staticType != null &&
+ node.staticType.isDynamic &&
+ node.staticElement == null) {
+ return null;
+ }
+ AstNode parent = node.parent;
+ if (parent is MethodInvocation) {
+ MethodInvocation invocation = parent;
+ if (identical(invocation.methodName, node)) {
+ Expression target = invocation.realTarget;
+ DartType targetType = target == null ? null : target.staticType;
+ if (targetType == null || targetType.isDynamic) {
+ return null;
+ }
+ }
+ }
+ return _checkResolved(node, node.staticElement, null);
+ }
+
+ Object _checkResolved(
+ AstNode node, Element element, Predicate<Element> predicate) {
+ if (element == null) {
+ if (_knownExceptions == null || !_knownExceptions.contains(node)) {
+ _unresolvedNodes.add(node);
+ }
+ } else if (predicate != null) {
+ if (!predicate(element)) {
+ _wrongTypedNodes.add(node);
+ }
+ }
+ return null;
+ }
+
+ String _getFileName(AstNode node) {
+ // TODO (jwren) there are two copies of this method, one here and one in
+ // StaticTypeVerifier, they should be resolved into a single method
+ if (node != null) {
+ AstNode root = node.root;
+ if (root is CompilationUnit) {
+ CompilationUnit rootCU = root;
+ if (rootCU.element != null) {
+ return rootCU.element.source.fullName;
+ } else {
+ return "<unknown file- CompilationUnit.getElement() returned null>";
+ }
+ } else {
+ return "<unknown file- CompilationUnit.getRoot() is not a CompilationUnit>";
+ }
+ }
+ return "<unknown file- ASTNode is null>";
+ }
+
+ void _printNodes(StringBuffer buffer, List<AstNode> nodes) {
+ for (AstNode identifier in nodes) {
+ buffer.write(" ");
+ buffer.write(identifier.toString());
+ buffer.write(" (");
+ buffer.write(_getFileName(identifier));
+ buffer.write(" : ");
+ buffer.write(identifier.offset);
+ buffer.writeln(")");
+ }
+ }
+}
+
class ResolverTestCase extends EngineTestCase {
/**
* The analysis context used to parse the compilation units being resolved.
@@ -126,262 +399,38 @@ class ResolverTestCase extends EngineTestCase {
assertErrors(source, errors);
verify([source]);
}
-
- /**
- * Asserts that [code] has errors with the given error codes.
- *
- * Like [assertErrors], but takes a string of source code.
- */
- void assertErrorsInUnverifiedCode(String code, List<ErrorCode> errors) {
- Source source = addSource(code);
- computeLibrarySourceErrors(source);
- assertErrors(source, errors);
- }
-
- /**
- * Assert that no errors have been reported against the given source.
- *
- * @param source the source against which no errors should have been reported
- * @throws AnalysisException if the reported errors could not be computed
- * @throws AssertionFailedError if any errors have been reported
- */
- void assertNoErrors(Source source) {
- assertErrors(source);
- }
-
- /**
- * Asserts that [code] has no errors or warnings.
- */
- // TODO(rnystrom): Use this in more tests that have the same structure.
- void assertNoErrorsInCode(String code) {
- Source source = addSource(code);
- computeLibrarySourceErrors(source);
- assertNoErrors(source);
- verify([source]);
- }
-
- /**
- * Cache the source file content in the source factory but don't add the source to the analysis
- * context. The file path should be absolute.
- *
- * @param filePath the path of the file being cached
- * @param contents the contents to be returned by the content provider for the specified file
- * @return the source object representing the cached file
- */
- Source cacheSource(String filePath, String contents) {
- Source source = new FileBasedSource(FileUtilities2.createFile(filePath));
- analysisContext2.setContents(source, contents);
- return source;
- }
-
- /**
- * Change the contents of the given [source] to the given [contents].
- */
- void changeSource(Source source, String contents) {
- analysisContext2.setContents(source, contents);
- ChangeSet changeSet = new ChangeSet();
- changeSet.changedSource(source);
- analysisContext2.applyChanges(changeSet);
- }
-
- /**
- * Computes errors for the given [librarySource].
- * This assumes that the given [librarySource] and its parts have already
- * been added to the content provider using the method [addNamedSource].
- */
- void computeLibrarySourceErrors(Source librarySource) {
- analysisContext.computeErrors(librarySource);
- }
-
- /**
- * Create a library element that represents a library named `"test"` containing a single
- * empty compilation unit.
- *
- * @return the library element that was created
- */
- LibraryElementImpl createDefaultTestLibrary() =>
- createTestLibrary(AnalysisContextFactory.contextWithCore(), "test");
-
- /**
- * Create a library element that represents a library with the given name containing a single
- * empty compilation unit.
- *
- * @param libraryName the name of the library to be created
- * @return the library element that was created
- */
- LibraryElementImpl createTestLibrary(
- AnalysisContext context, String libraryName,
- [List<String> typeNames]) {
- String fileName = "$libraryName.dart";
- FileBasedSource definingCompilationUnitSource =
- createNamedSource(fileName);
- List<CompilationUnitElement> sourcedCompilationUnits;
- if (typeNames == null) {
- sourcedCompilationUnits = CompilationUnitElement.EMPTY_LIST;
- } else {
- int count = typeNames.length;
- sourcedCompilationUnits = new List<CompilationUnitElement>(count);
- for (int i = 0; i < count; i++) {
- String typeName = typeNames[i];
- ClassElementImpl type =
- new ClassElementImpl.forNode(AstFactory.identifier3(typeName));
- String fileName = "$typeName.dart";
- CompilationUnitElementImpl compilationUnit =
- new CompilationUnitElementImpl(fileName);
- compilationUnit.source = createNamedSource(fileName);
- compilationUnit.librarySource = definingCompilationUnitSource;
- compilationUnit.types = <ClassElement>[type];
- sourcedCompilationUnits[i] = compilationUnit;
- }
- }
- CompilationUnitElementImpl compilationUnit =
- new CompilationUnitElementImpl(fileName);
- compilationUnit.librarySource =
- compilationUnit.source = definingCompilationUnitSource;
- LibraryElementImpl library = new LibraryElementImpl.forNode(
- context, AstFactory.libraryIdentifier2([libraryName]));
- library.definingCompilationUnit = compilationUnit;
- library.parts = sourcedCompilationUnits;
- return library;
- }
-
- Expression findTopLevelConstantExpression(
- CompilationUnit compilationUnit, String name) =>
- findTopLevelDeclaration(compilationUnit, name).initializer;
-
- VariableDeclaration findTopLevelDeclaration(
- CompilationUnit compilationUnit, String name) {
- for (CompilationUnitMember member in compilationUnit.declarations) {
- if (member is TopLevelVariableDeclaration) {
- for (VariableDeclaration variable in member.variables.variables) {
- if (variable.name.name == name) {
- return variable;
- }
- }
- }
- }
- return null;
- // Not found
- }
-
- /**
- * In the rare cases we want to group several tests into single "test_" method, so need a way to
- * reset test instance to reuse it.
- */
- void reset() {
- analysisContext2 = AnalysisContextFactory.contextWithCore();
- }
-
- /**
- * Reset the analysis context to have the given options applied.
- *
- * @param options the analysis options to be applied to the context
- */
- void resetWithOptions(AnalysisOptions options) {
- analysisContext2 =
- AnalysisContextFactory.contextWithCoreAndOptions(options);
- }
-
- /**
- * Given a library and all of its parts, resolve the contents of the library and the contents of
- * the parts. This assumes that the sources for the library and its parts have already been added
- * to the content provider using the method [addNamedSource].
- *
- * @param librarySource the source for the compilation unit that defines the library
- * @return the element representing the resolved library
- * @throws AnalysisException if the analysis could not be performed
- */
- LibraryElement resolve2(Source librarySource) =>
- analysisContext2.computeLibraryElement(librarySource);
-
- /**
- * Return the resolved compilation unit corresponding to the given source in the given library.
- *
- * @param source the source of the compilation unit to be returned
- * @param library the library in which the compilation unit is to be resolved
- * @return the resolved compilation unit
- * @throws Exception if the compilation unit could not be resolved
- */
- CompilationUnit resolveCompilationUnit(
- Source source, LibraryElement library) =>
- analysisContext2.resolveCompilationUnit(source, library);
-
- CompilationUnit resolveSource(String sourceText) =>
- resolveSource2("/test.dart", sourceText);
-
- CompilationUnit resolveSource2(String fileName, String sourceText) {
- Source source = addNamedSource(fileName, sourceText);
- LibraryElement library = analysisContext.computeLibraryElement(source);
- return analysisContext.resolveCompilationUnit(source, library);
- }
-
- Source resolveSources(List<String> sourceTexts) {
- for (int i = 0; i < sourceTexts.length; i++) {
- CompilationUnit unit =
- resolveSource2("/lib${i + 1}.dart", sourceTexts[i]);
- // reference the source if this is the last source
- if (i + 1 == sourceTexts.length) {
- return unit.element.source;
- }
- }
- return null;
- }
-
- void resolveWithAndWithoutExperimental(
- List<String> strSources,
- List<ErrorCode> codesWithoutExperimental,
- List<ErrorCode> codesWithExperimental) {
- // Setup analysis context as non-experimental
- AnalysisOptionsImpl options = new AnalysisOptionsImpl();
-// options.enableDeferredLoading = false;
- resetWithOptions(options);
- // Analysis and assertions
- Source source = resolveSources(strSources);
- assertErrors(source, codesWithoutExperimental);
- verify([source]);
- // Setup analysis context as experimental
- reset();
- // Analysis and assertions
- source = resolveSources(strSources);
- assertErrors(source, codesWithExperimental);
- verify([source]);
- }
-
- void resolveWithErrors(List<String> strSources, List<ErrorCode> codes) {
- // Analysis and assertions
- Source source = resolveSources(strSources);
- assertErrors(source, codes);
- verify([source]);
- }
-
- @override
- void setUp() {
- ElementFactory.flushStaticState();
- super.setUp();
- reset();
+
+ /**
+ * Asserts that [code] has errors with the given error codes.
+ *
+ * Like [assertErrors], but takes a string of source code.
+ */
+ void assertErrorsInUnverifiedCode(String code, List<ErrorCode> errors) {
+ Source source = addSource(code);
+ computeLibrarySourceErrors(source);
+ assertErrors(source, errors);
}
- @override
- void tearDown() {
- analysisContext2 = null;
- super.tearDown();
+ /**
+ * Assert that no errors have been reported against the given source.
+ *
+ * @param source the source against which no errors should have been reported
+ * @throws AnalysisException if the reported errors could not be computed
+ * @throws AssertionFailedError if any errors have been reported
+ */
+ void assertNoErrors(Source source) {
+ assertErrors(source);
}
/**
- * Verify that all of the identifiers in the compilation units associated with
- * the given [sources] have been resolved.
+ * Asserts that [code] has no errors or warnings.
*/
- void verify(List<Source> sources) {
- ResolutionVerifier verifier = new ResolutionVerifier();
- for (Source source in sources) {
- List<Source> libraries = analysisContext2.getLibrariesContaining(source);
- for (Source library in libraries) {
- analysisContext2
- .resolveCompilationUnit2(source, library)
- .accept(verifier);
- }
- }
- verifier.assertResolved();
+ // TODO(rnystrom): Use this in more tests that have the same structure.
+ void assertNoErrorsInCode(String code) {
+ Source source = addSource(code);
+ computeLibrarySourceErrors(source);
+ assertNoErrors(source);
+ verify([source]);
}
/**
@@ -424,6 +473,48 @@ class ResolverTestCase extends EngineTestCase {
}
/**
+ * Cache the source file content in the source factory but don't add the source to the analysis
+ * context. The file path should be absolute.
+ *
+ * @param filePath the path of the file being cached
+ * @param contents the contents to be returned by the content provider for the specified file
+ * @return the source object representing the cached file
+ */
+ Source cacheSource(String filePath, String contents) {
+ Source source = new FileBasedSource(FileUtilities2.createFile(filePath));
+ analysisContext2.setContents(source, contents);
+ return source;
+ }
+
+ /**
+ * Change the contents of the given [source] to the given [contents].
+ */
+ void changeSource(Source source, String contents) {
+ analysisContext2.setContents(source, contents);
+ ChangeSet changeSet = new ChangeSet();
+ changeSet.changedSource(source);
+ analysisContext2.applyChanges(changeSet);
+ }
+
+ /**
+ * Computes errors for the given [librarySource].
+ * This assumes that the given [librarySource] and its parts have already
+ * been added to the content provider using the method [addNamedSource].
+ */
+ void computeLibrarySourceErrors(Source librarySource) {
+ analysisContext.computeErrors(librarySource);
+ }
+
+ /**
+ * Create a library element that represents a library named `"test"` containing a single
+ * empty compilation unit.
+ *
+ * @return the library element that was created
+ */
+ LibraryElementImpl createDefaultTestLibrary() =>
+ createTestLibrary(AnalysisContextFactory.contextWithCore(), "test");
+
+ /**
* Create a source object representing a file with the given [fileName] and
* give it an empty content. Return the source that was created.
*/
@@ -435,6 +526,49 @@ class ResolverTestCase extends EngineTestCase {
}
/**
+ * Create a library element that represents a library with the given name containing a single
+ * empty compilation unit.
+ *
+ * @param libraryName the name of the library to be created
+ * @return the library element that was created
+ */
+ LibraryElementImpl createTestLibrary(
+ AnalysisContext context, String libraryName,
+ [List<String> typeNames]) {
+ String fileName = "$libraryName.dart";
+ FileBasedSource definingCompilationUnitSource =
+ createNamedSource(fileName);
+ List<CompilationUnitElement> sourcedCompilationUnits;
+ if (typeNames == null) {
+ sourcedCompilationUnits = CompilationUnitElement.EMPTY_LIST;
+ } else {
+ int count = typeNames.length;
+ sourcedCompilationUnits = new List<CompilationUnitElement>(count);
+ for (int i = 0; i < count; i++) {
+ String typeName = typeNames[i];
+ ClassElementImpl type =
+ new ClassElementImpl.forNode(AstFactory.identifier3(typeName));
+ String fileName = "$typeName.dart";
+ CompilationUnitElementImpl compilationUnit =
+ new CompilationUnitElementImpl(fileName);
+ compilationUnit.source = createNamedSource(fileName);
+ compilationUnit.librarySource = definingCompilationUnitSource;
+ compilationUnit.types = <ClassElement>[type];
+ sourcedCompilationUnits[i] = compilationUnit;
+ }
+ }
+ CompilationUnitElementImpl compilationUnit =
+ new CompilationUnitElementImpl(fileName);
+ compilationUnit.librarySource =
+ compilationUnit.source = definingCompilationUnitSource;
+ LibraryElementImpl library = new LibraryElementImpl.forNode(
+ context, AstFactory.libraryIdentifier2([libraryName]));
+ library.definingCompilationUnit = compilationUnit;
+ library.parts = sourcedCompilationUnits;
+ return library;
+ }
+
+ /**
* Return the `SimpleIdentifier` marked by `marker`. The source code must have no
* errors and be verifiable.
*
@@ -463,278 +597,144 @@ class ResolverTestCase extends EngineTestCase {
throw new JavaException("Unexexpected assertion failure: $exception");
}
}
-}
-
-/**
- * An AST visitor used to verify that all of the nodes in an AST structure that
- * should have been resolved were resolved.
- */
-class ResolutionVerifier extends RecursiveAstVisitor<Object> {
- /**
- * A set containing nodes that are known to not be resolvable and should
- * therefore not cause the test to fail.
- */
- final Set<AstNode> _knownExceptions;
-
- /**
- * A list containing all of the AST nodes that were not resolved.
- */
- List<AstNode> _unresolvedNodes = new List<AstNode>();
-
- /**
- * A list containing all of the AST nodes that were resolved to an element of
- * the wrong type.
- */
- List<AstNode> _wrongTypedNodes = new List<AstNode>();
-
- /**
- * Initialize a newly created verifier to verify that all of the identifiers
- * in the visited AST structures that are expected to have been resolved have
- * an element associated with them. Nodes in the set of [_knownExceptions] are
- * not expected to have been resolved, even if they normally would have been
- * expected to have been resolved.
- */
- ResolutionVerifier([this._knownExceptions]);
-
- /**
- * Assert that all of the visited identifiers were resolved.
- */
- void assertResolved() {
- if (!_unresolvedNodes.isEmpty || !_wrongTypedNodes.isEmpty) {
- StringBuffer buffer = new StringBuffer();
- if (!_unresolvedNodes.isEmpty) {
- buffer.write("Failed to resolve ");
- buffer.write(_unresolvedNodes.length);
- buffer.writeln(" nodes:");
- _printNodes(buffer, _unresolvedNodes);
- }
- if (!_wrongTypedNodes.isEmpty) {
- buffer.write("Resolved ");
- buffer.write(_wrongTypedNodes.length);
- buffer.writeln(" to the wrong type of element:");
- _printNodes(buffer, _wrongTypedNodes);
- }
- fail(buffer.toString());
- }
- }
-
- @override
- Object visitAnnotation(Annotation node) {
- node.visitChildren(this);
- ElementAnnotation elementAnnotation = node.elementAnnotation;
- if (elementAnnotation == null) {
- if (_knownExceptions == null || !_knownExceptions.contains(node)) {
- _unresolvedNodes.add(node);
- }
- } else if (elementAnnotation is! ElementAnnotation) {
- _wrongTypedNodes.add(node);
- }
- return null;
- }
-
- @override
- Object visitBinaryExpression(BinaryExpression node) {
- node.visitChildren(this);
- if (!node.operator.isUserDefinableOperator) {
- return null;
- }
- DartType operandType = node.leftOperand.staticType;
- if (operandType == null || operandType.isDynamic) {
- return null;
- }
- return _checkResolved(
- node, node.staticElement, (node) => node is MethodElement);
- }
-
- @override
- Object visitCommentReference(CommentReference node) => null;
-
- @override
- Object visitCompilationUnit(CompilationUnit node) {
- node.visitChildren(this);
- return _checkResolved(
- node, node.element, (node) => node is CompilationUnitElement);
- }
-
- @override
- Object visitExportDirective(ExportDirective node) =>
- _checkResolved(node, node.element, (node) => node is ExportElement);
- @override
- Object visitFunctionDeclaration(FunctionDeclaration node) {
- node.visitChildren(this);
- if (node.element is LibraryElement) {
- _wrongTypedNodes.add(node);
- }
- return null;
- }
-
- @override
- Object visitFunctionExpressionInvocation(FunctionExpressionInvocation node) {
- node.visitChildren(this);
- // TODO(brianwilkerson) If we start resolving function expressions, then
- // conditionally check to see whether the node was resolved correctly.
- return null;
- //checkResolved(node, node.getElement(), FunctionElement.class);
- }
+ Expression findTopLevelConstantExpression(
+ CompilationUnit compilationUnit, String name) =>
+ findTopLevelDeclaration(compilationUnit, name).initializer;
- @override
- Object visitImportDirective(ImportDirective node) {
- // Not sure how to test the combinators given that it isn't an error if the
- // names are not defined.
- _checkResolved(node, node.element, (node) => node is ImportElement);
- SimpleIdentifier prefix = node.prefix;
- if (prefix == null) {
- return null;
+ VariableDeclaration findTopLevelDeclaration(
+ CompilationUnit compilationUnit, String name) {
+ for (CompilationUnitMember member in compilationUnit.declarations) {
+ if (member is TopLevelVariableDeclaration) {
+ for (VariableDeclaration variable in member.variables.variables) {
+ if (variable.name.name == name) {
+ return variable;
+ }
+ }
+ }
}
- return _checkResolved(
- prefix, prefix.staticElement, (node) => node is PrefixElement);
+ return null;
+ // Not found
}
- @override
- Object visitIndexExpression(IndexExpression node) {
- node.visitChildren(this);
- DartType targetType = node.realTarget.staticType;
- if (targetType == null || targetType.isDynamic) {
- return null;
- }
- return _checkResolved(
- node, node.staticElement, (node) => node is MethodElement);
+ /**
+ * In the rare cases we want to group several tests into single "test_" method, so need a way to
+ * reset test instance to reuse it.
+ */
+ void reset() {
+ analysisContext2 = AnalysisContextFactory.contextWithCore();
}
- @override
- Object visitLibraryDirective(LibraryDirective node) =>
- _checkResolved(node, node.element, (node) => node is LibraryElement);
+ /**
+ * Reset the analysis context to have the given options applied.
+ *
+ * @param options the analysis options to be applied to the context
+ */
+ void resetWithOptions(AnalysisOptions options) {
+ analysisContext2 =
+ AnalysisContextFactory.contextWithCoreAndOptions(options);
+ }
- @override
- Object visitNamedExpression(NamedExpression node) =>
- node.expression.accept(this);
+ /**
+ * Given a library and all of its parts, resolve the contents of the library and the contents of
+ * the parts. This assumes that the sources for the library and its parts have already been added
+ * to the content provider using the method [addNamedSource].
+ *
+ * @param librarySource the source for the compilation unit that defines the library
+ * @return the element representing the resolved library
+ * @throws AnalysisException if the analysis could not be performed
+ */
+ LibraryElement resolve2(Source librarySource) =>
+ analysisContext2.computeLibraryElement(librarySource);
- @override
- Object visitPartDirective(PartDirective node) => _checkResolved(
- node, node.element, (node) => node is CompilationUnitElement);
+ /**
+ * Return the resolved compilation unit corresponding to the given source in the given library.
+ *
+ * @param source the source of the compilation unit to be returned
+ * @param library the library in which the compilation unit is to be resolved
+ * @return the resolved compilation unit
+ * @throws Exception if the compilation unit could not be resolved
+ */
+ CompilationUnit resolveCompilationUnit(
+ Source source, LibraryElement library) =>
+ analysisContext2.resolveCompilationUnit(source, library);
- @override
- Object visitPartOfDirective(PartOfDirective node) =>
- _checkResolved(node, node.element, (node) => node is LibraryElement);
+ CompilationUnit resolveSource(String sourceText) =>
+ resolveSource2("/test.dart", sourceText);
- @override
- Object visitPostfixExpression(PostfixExpression node) {
- node.visitChildren(this);
- if (!node.operator.isUserDefinableOperator) {
- return null;
- }
- DartType operandType = node.operand.staticType;
- if (operandType == null || operandType.isDynamic) {
- return null;
- }
- return _checkResolved(
- node, node.staticElement, (node) => node is MethodElement);
+ CompilationUnit resolveSource2(String fileName, String sourceText) {
+ Source source = addNamedSource(fileName, sourceText);
+ LibraryElement library = analysisContext.computeLibraryElement(source);
+ return analysisContext.resolveCompilationUnit(source, library);
}
- @override
- Object visitPrefixedIdentifier(PrefixedIdentifier node) {
- SimpleIdentifier prefix = node.prefix;
- prefix.accept(this);
- DartType prefixType = prefix.staticType;
- if (prefixType == null || prefixType.isDynamic) {
- return null;
+ Source resolveSources(List<String> sourceTexts) {
+ for (int i = 0; i < sourceTexts.length; i++) {
+ CompilationUnit unit =
+ resolveSource2("/lib${i + 1}.dart", sourceTexts[i]);
+ // reference the source if this is the last source
+ if (i + 1 == sourceTexts.length) {
+ return unit.element.source;
+ }
}
- return _checkResolved(node, node.staticElement, null);
+ return null;
}
- @override
- Object visitPrefixExpression(PrefixExpression node) {
- node.visitChildren(this);
- if (!node.operator.isUserDefinableOperator) {
- return null;
- }
- DartType operandType = node.operand.staticType;
- if (operandType == null || operandType.isDynamic) {
- return null;
- }
- return _checkResolved(
- node, node.staticElement, (node) => node is MethodElement);
+ void resolveWithAndWithoutExperimental(
+ List<String> strSources,
+ List<ErrorCode> codesWithoutExperimental,
+ List<ErrorCode> codesWithExperimental) {
+ // Setup analysis context as non-experimental
+ AnalysisOptionsImpl options = new AnalysisOptionsImpl();
+// options.enableDeferredLoading = false;
+ resetWithOptions(options);
+ // Analysis and assertions
+ Source source = resolveSources(strSources);
+ assertErrors(source, codesWithoutExperimental);
+ verify([source]);
+ // Setup analysis context as experimental
+ reset();
+ // Analysis and assertions
+ source = resolveSources(strSources);
+ assertErrors(source, codesWithExperimental);
+ verify([source]);
}
- @override
- Object visitPropertyAccess(PropertyAccess node) {
- Expression target = node.realTarget;
- target.accept(this);
- DartType targetType = target.staticType;
- if (targetType == null || targetType.isDynamic) {
- return null;
- }
- return node.propertyName.accept(this);
+ void resolveWithErrors(List<String> strSources, List<ErrorCode> codes) {
+ // Analysis and assertions
+ Source source = resolveSources(strSources);
+ assertErrors(source, codes);
+ verify([source]);
}
@override
- Object visitSimpleIdentifier(SimpleIdentifier node) {
- if (node.name == "void") {
- return null;
- }
- if (node.staticType != null &&
- node.staticType.isDynamic &&
- node.staticElement == null) {
- return null;
- }
- AstNode parent = node.parent;
- if (parent is MethodInvocation) {
- MethodInvocation invocation = parent;
- if (identical(invocation.methodName, node)) {
- Expression target = invocation.realTarget;
- DartType targetType = target == null ? null : target.staticType;
- if (targetType == null || targetType.isDynamic) {
- return null;
- }
- }
- }
- return _checkResolved(node, node.staticElement, null);
+ void setUp() {
+ ElementFactory.flushStaticState();
+ super.setUp();
+ reset();
}
- Object _checkResolved(
- AstNode node, Element element, Predicate<Element> predicate) {
- if (element == null) {
- if (_knownExceptions == null || !_knownExceptions.contains(node)) {
- _unresolvedNodes.add(node);
- }
- } else if (predicate != null) {
- if (!predicate(element)) {
- _wrongTypedNodes.add(node);
- }
- }
- return null;
+ @override
+ void tearDown() {
+ analysisContext2 = null;
+ super.tearDown();
}
- String _getFileName(AstNode node) {
- // TODO (jwren) there are two copies of this method, one here and one in
- // StaticTypeVerifier, they should be resolved into a single method
- if (node != null) {
- AstNode root = node.root;
- if (root is CompilationUnit) {
- CompilationUnit rootCU = root;
- if (rootCU.element != null) {
- return rootCU.element.source.fullName;
- } else {
- return "<unknown file- CompilationUnit.getElement() returned null>";
- }
- } else {
- return "<unknown file- CompilationUnit.getRoot() is not a CompilationUnit>";
+ /**
+ * Verify that all of the identifiers in the compilation units associated with
+ * the given [sources] have been resolved.
+ */
+ void verify(List<Source> sources) {
+ ResolutionVerifier verifier = new ResolutionVerifier();
+ for (Source source in sources) {
+ List<Source> libraries = analysisContext2.getLibrariesContaining(source);
+ for (Source library in libraries) {
+ analysisContext2
+ .resolveCompilationUnit2(source, library)
+ .accept(verifier);
}
}
- return "<unknown file- ASTNode is null>";
- }
-
- void _printNodes(StringBuffer buffer, List<AstNode> nodes) {
- for (AstNode identifier in nodes) {
- buffer.write(" ");
- buffer.write(identifier.toString());
- buffer.write(" (");
- buffer.write(_getFileName(identifier));
- buffer.write(" : ");
- buffer.write(identifier.offset);
- buffer.writeln(")");
- }
+ verifier.assertResolved();
}
}
@@ -808,20 +808,6 @@ class StaticTypeAnalyzer2TestShared extends ResolverTestCase {
}
}
- /**
- * Validates that [type] matches [expected].
- *
- * If [expected] is a string, validates that the type stringifies to that
- * text. Otherwise, [expected] is used directly a [Matcher] to match the type.
- */
- _expectType(DartType type, expected) {
- if (expected is String) {
- expect(type.toString(), expected);
- } else {
- expect(type, expected);
- }
- }
-
SimpleIdentifier findIdentifier(String search) {
SimpleIdentifier identifier = EngineTestCase.findNode(
testUnit, testCode, search, (node) => node is SimpleIdentifier);
@@ -836,4 +822,18 @@ class StaticTypeAnalyzer2TestShared extends ResolverTestCase {
verify([testSource]);
testUnit = resolveCompilationUnit(testSource, library);
}
+
+ /**
+ * Validates that [type] matches [expected].
+ *
+ * If [expected] is a string, validates that the type stringifies to that
+ * text. Otherwise, [expected] is used directly a [Matcher] to match the type.
+ */
+ _expectType(DartType type, expected) {
+ if (expected is String) {
+ expect(type.toString(), expected);
+ } else {
+ expect(type, expected);
+ }
+ }
}
« no previous file with comments | « pkg/analyzer/test/generated/incremental_resolver_test.dart ('k') | pkg/analyzer/test/generated/static_type_analyzer_test.dart » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698