mirror of
https://github.com/dart-lang/sdk
synced 2024-09-16 02:07:06 +00:00
Make FindElement more self-consistent.
R=brianwilkerson@google.com Change-Id: I74bc21a5e6ead36c9a631fc529497108001947ef Reviewed-on: https://dart-review.googlesource.com/c/87269 Reviewed-by: Brian Wilkerson <brianwilkerson@google.com> Commit-Queue: Konstantin Shcheglov <scheglov@google.com>
This commit is contained in:
parent
9de66d87b8
commit
6146095f73
|
@ -247,7 +247,7 @@ main() {
|
|||
assertType(creation, 'B');
|
||||
|
||||
var fRef = left.propertyName;
|
||||
assertElement(fRef, findElement.setter('f', className: 'A'));
|
||||
assertElement(fRef, findElement.setter('f', of: 'A'));
|
||||
assertType(fRef, 'int');
|
||||
|
||||
var right = assignment.rightHandSide;
|
||||
|
|
|
@ -141,7 +141,7 @@ class C extends B {
|
|||
assertNoTestErrors();
|
||||
assertElement(
|
||||
findNode.simple('foo = 0;'),
|
||||
findElement.setter('foo', className: 'A'),
|
||||
findElement.setter('foo', of: 'A'),
|
||||
);
|
||||
}
|
||||
|
||||
|
|
|
@ -61,7 +61,7 @@ main() {}
|
|||
);
|
||||
assertElement(
|
||||
findNode.simple('named]'),
|
||||
findElement.constructor('named', className: 'A'),
|
||||
findElement.constructor('named', of: 'A'),
|
||||
);
|
||||
}
|
||||
|
||||
|
@ -250,7 +250,7 @@ class B extends A {
|
|||
await resolveTestFile();
|
||||
assertNoTestErrors();
|
||||
|
||||
var x = findElement.setter('x', className: 'A');
|
||||
var x = findElement.setter('x', of: 'A');
|
||||
assertElement(findNode.simple('x] in A'), x);
|
||||
assertElement(findNode.simple('x] in B'), x);
|
||||
}
|
||||
|
|
|
@ -9,6 +9,7 @@ import 'package:test/test.dart';
|
|||
|
||||
import 'function_ast_visitor.dart';
|
||||
|
||||
/// Helper for finding elements declared in the resolved [unit].
|
||||
class FindElement {
|
||||
final CompilationUnit unit;
|
||||
|
||||
|
@ -22,18 +23,18 @@ class FindElement {
|
|||
return class_;
|
||||
}
|
||||
}
|
||||
fail('Not found class: $name');
|
||||
fail('Not found: $name');
|
||||
}
|
||||
|
||||
ConstructorElement constructor(String name, {String className}) {
|
||||
ConstructorElement constructor(String name, {String of}) {
|
||||
assert(name != '');
|
||||
ConstructorElement result;
|
||||
for (var class_ in unitElement.types) {
|
||||
if (className == null || class_.name == className) {
|
||||
if (of == null || class_.name == of) {
|
||||
for (var constructor in class_.constructors) {
|
||||
if (constructor.name == name) {
|
||||
if (result != null) {
|
||||
throw new StateError('Not constructor name: $name');
|
||||
fail('Not unique: $name');
|
||||
}
|
||||
result = constructor;
|
||||
}
|
||||
|
@ -43,7 +44,7 @@ class FindElement {
|
|||
if (result != null) {
|
||||
return result;
|
||||
}
|
||||
fail('Not found constructor: $name');
|
||||
fail('Not found: $name');
|
||||
}
|
||||
|
||||
ClassElement enum_(String name) {
|
||||
|
@ -52,49 +53,67 @@ class FindElement {
|
|||
return enum_;
|
||||
}
|
||||
}
|
||||
fail('Not found enum: $name');
|
||||
fail('Not found: $name');
|
||||
}
|
||||
|
||||
ExportElement export(String targetUri) {
|
||||
ExportElement exportElement;
|
||||
ExportElement result;
|
||||
|
||||
for (var export in unitElement.library.exports) {
|
||||
var exportedUri = export.exportedLibrary.source.uri.toString();
|
||||
if (exportedUri == targetUri) {
|
||||
if (exportElement != null) {
|
||||
throw new StateError('Not unique $targetUri export.');
|
||||
if (result != null) {
|
||||
fail('Not unique: $targetUri');
|
||||
}
|
||||
exportElement = export;
|
||||
result = export;
|
||||
}
|
||||
}
|
||||
if (exportElement != null) {
|
||||
return exportElement;
|
||||
|
||||
if (result != null) {
|
||||
return result;
|
||||
}
|
||||
fail('Not found export: $targetUri');
|
||||
fail('Not found: $targetUri');
|
||||
}
|
||||
|
||||
FieldElement field(String name) {
|
||||
FieldElement field(String name, {String of}) {
|
||||
FieldElement result;
|
||||
|
||||
void findIn(List<FieldElement> fields) {
|
||||
for (var field in fields) {
|
||||
if (field.name == name) {
|
||||
if (result != null) {
|
||||
fail('Not unique: $name');
|
||||
}
|
||||
result = field;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
for (var enum_ in unitElement.enums) {
|
||||
for (var field in enum_.fields) {
|
||||
if (field.name == name) {
|
||||
return field;
|
||||
}
|
||||
}
|
||||
}
|
||||
for (var mixin in unitElement.mixins) {
|
||||
for (var field in mixin.fields) {
|
||||
if (field.name == name) {
|
||||
return field;
|
||||
}
|
||||
if (of != null && enum_.name != of) {
|
||||
continue;
|
||||
}
|
||||
findIn(enum_.fields);
|
||||
}
|
||||
|
||||
for (var class_ in unitElement.types) {
|
||||
for (var field in class_.fields) {
|
||||
if (field.name == name) {
|
||||
return field;
|
||||
}
|
||||
if (of != null && class_.name != of) {
|
||||
continue;
|
||||
}
|
||||
findIn(class_.fields);
|
||||
}
|
||||
fail('Not found field: $name');
|
||||
|
||||
for (var mixin in unitElement.mixins) {
|
||||
if (of != null && mixin.name != of) {
|
||||
continue;
|
||||
}
|
||||
findIn(mixin.fields);
|
||||
}
|
||||
|
||||
if (result != null) {
|
||||
return result;
|
||||
}
|
||||
fail('Not found: $name');
|
||||
}
|
||||
|
||||
FunctionElement function(String name) {
|
||||
|
@ -103,7 +122,7 @@ class FindElement {
|
|||
return function;
|
||||
}
|
||||
}
|
||||
fail('Not found top-level function: $name');
|
||||
fail('Not found: $name');
|
||||
}
|
||||
|
||||
GenericTypeAliasElement genericTypeAlias(String name) {
|
||||
|
@ -112,45 +131,67 @@ class FindElement {
|
|||
return element;
|
||||
}
|
||||
}
|
||||
fail('Not found generic type alias: $name');
|
||||
fail('Not found: $name');
|
||||
}
|
||||
|
||||
PropertyAccessorElement getter(String name, {String of}) {
|
||||
for (var enum_ in unitElement.enums) {
|
||||
for (var accessor in enum_.accessors) {
|
||||
PropertyAccessorElement result;
|
||||
|
||||
void findIn(List<PropertyAccessorElement> accessors) {
|
||||
for (var accessor in accessors) {
|
||||
if (accessor.isGetter && accessor.displayName == name) {
|
||||
return accessor;
|
||||
if (result != null) {
|
||||
fail('Not unique: $name');
|
||||
}
|
||||
result = accessor;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
for (var enum_ in unitElement.enums) {
|
||||
if (of != null && enum_.name != of) {
|
||||
continue;
|
||||
}
|
||||
findIn(enum_.accessors);
|
||||
}
|
||||
|
||||
for (var class_ in unitElement.types) {
|
||||
if (of != null && class_.name != of) {
|
||||
continue;
|
||||
}
|
||||
for (var accessor in class_.accessors) {
|
||||
if (accessor.isGetter && accessor.displayName == name) {
|
||||
return accessor;
|
||||
}
|
||||
}
|
||||
findIn(class_.accessors);
|
||||
}
|
||||
fail('Not found class accessor: $name');
|
||||
|
||||
for (var mixin in unitElement.mixins) {
|
||||
if (of != null && mixin.name != of) {
|
||||
continue;
|
||||
}
|
||||
findIn(mixin.accessors);
|
||||
}
|
||||
|
||||
if (result != null) {
|
||||
return result;
|
||||
}
|
||||
fail('Not found: $name');
|
||||
}
|
||||
|
||||
ImportElement import(String targetUri) {
|
||||
ImportElement importElement;
|
||||
|
||||
for (var import in unitElement.library.imports) {
|
||||
var importedUri = import.importedLibrary.source.uri.toString();
|
||||
if (importedUri == targetUri) {
|
||||
if (importElement != null) {
|
||||
throw new StateError('Not unique $targetUri import.');
|
||||
fail('Not unique: $targetUri');
|
||||
}
|
||||
importElement = import;
|
||||
}
|
||||
}
|
||||
|
||||
if (importElement != null) {
|
||||
return importElement;
|
||||
}
|
||||
fail('Not found import: $targetUri');
|
||||
fail('Not found: $targetUri');
|
||||
}
|
||||
|
||||
InterfaceType interfaceType(String name) {
|
||||
|
@ -159,38 +200,42 @@ class FindElement {
|
|||
|
||||
FunctionElement localFunction(String name) {
|
||||
FunctionElement result;
|
||||
|
||||
unit.accept(new FunctionAstVisitor(
|
||||
functionDeclarationStatement: (node) {
|
||||
var element = node.functionDeclaration.declaredElement;
|
||||
if (element is FunctionElement) {
|
||||
if (result != null) {
|
||||
throw new StateError('Local function name $name is not unique.');
|
||||
fail('Not unique: $name');
|
||||
}
|
||||
result = element;
|
||||
}
|
||||
},
|
||||
));
|
||||
|
||||
if (result == null) {
|
||||
fail('Not found local function: $name');
|
||||
fail('Not found: $name');
|
||||
}
|
||||
return result;
|
||||
}
|
||||
|
||||
LocalVariableElement localVar(String name) {
|
||||
LocalVariableElement result;
|
||||
|
||||
unit.accept(new FunctionAstVisitor(
|
||||
variableDeclaration: (node) {
|
||||
var element = node.declaredElement;
|
||||
if (element is LocalVariableElement) {
|
||||
if (result != null) {
|
||||
throw new StateError('Local variable name $name is not unique.');
|
||||
fail('Not unique: $name');
|
||||
}
|
||||
result = element;
|
||||
}
|
||||
},
|
||||
));
|
||||
|
||||
if (result == null) {
|
||||
fail('Not found local variable: $name');
|
||||
fail('Not found: $name');
|
||||
}
|
||||
return result;
|
||||
}
|
||||
|
@ -202,7 +247,7 @@ class FindElement {
|
|||
for (var method in methods) {
|
||||
if (method.name == name) {
|
||||
if (result != null) {
|
||||
throw new StateError('Method name $name is not unique.');
|
||||
fail('Not unique: $name');
|
||||
}
|
||||
result = method;
|
||||
}
|
||||
|
@ -226,7 +271,7 @@ class FindElement {
|
|||
if (result != null) {
|
||||
return result;
|
||||
}
|
||||
fail('Not found class method: $name');
|
||||
fail('Not found: $name');
|
||||
}
|
||||
|
||||
ClassElement mixin(String name) {
|
||||
|
@ -235,73 +280,92 @@ class FindElement {
|
|||
return mixin;
|
||||
}
|
||||
}
|
||||
fail('Not found mixin: $name');
|
||||
fail('Not found: $name');
|
||||
}
|
||||
|
||||
ParameterElement parameter(String name) {
|
||||
ParameterElement parameterElement;
|
||||
void considerParameter(ParameterElement parameter) {
|
||||
if (parameter.name == name) {
|
||||
if (parameterElement != null) {
|
||||
throw new StateError('Parameter name $name is not unique.');
|
||||
ParameterElement result;
|
||||
|
||||
void findIn(List<ParameterElement> parameters) {
|
||||
for (var parameter in parameters) {
|
||||
if (parameter.name == name) {
|
||||
if (result != null) {
|
||||
fail('Not unique: $name');
|
||||
}
|
||||
result = parameter;
|
||||
}
|
||||
parameterElement = parameter;
|
||||
}
|
||||
}
|
||||
|
||||
for (var accessor in unitElement.accessors) {
|
||||
accessor.parameters.forEach(considerParameter);
|
||||
findIn(accessor.parameters);
|
||||
}
|
||||
|
||||
for (var function in unitElement.functions) {
|
||||
function.parameters.forEach(considerParameter);
|
||||
findIn(function.parameters);
|
||||
}
|
||||
|
||||
for (var function in unitElement.functionTypeAliases) {
|
||||
function.parameters.forEach(considerParameter);
|
||||
findIn(function.parameters);
|
||||
}
|
||||
|
||||
for (var class_ in unitElement.types) {
|
||||
for (var constructor in class_.constructors) {
|
||||
constructor.parameters.forEach(considerParameter);
|
||||
findIn(constructor.parameters);
|
||||
}
|
||||
for (var method in class_.methods) {
|
||||
method.parameters.forEach(considerParameter);
|
||||
findIn(method.parameters);
|
||||
}
|
||||
}
|
||||
if (parameterElement != null) {
|
||||
return parameterElement;
|
||||
|
||||
if (result != null) {
|
||||
return result;
|
||||
}
|
||||
fail('No parameter found with name $name');
|
||||
fail('Not found: $name');
|
||||
}
|
||||
|
||||
PrefixElement prefix(String name) {
|
||||
for (var import_ in unitElement.library.imports) {
|
||||
var prefix = import_.prefix;
|
||||
if (prefix != null && prefix.name == name) {
|
||||
if (prefix?.name == name) {
|
||||
return prefix;
|
||||
}
|
||||
}
|
||||
fail('Prefix not found: $name');
|
||||
fail('Not found: $name');
|
||||
}
|
||||
|
||||
PropertyAccessorElement setter(String name, {String className}) {
|
||||
PropertyAccessorElement setter(String name, {String of}) {
|
||||
PropertyAccessorElement result;
|
||||
for (var class_ in unitElement.types) {
|
||||
if (className != null && class_.name != className) {
|
||||
continue;
|
||||
}
|
||||
for (var accessor in class_.accessors) {
|
||||
|
||||
void findIn(List<PropertyAccessorElement> accessors) {
|
||||
for (var accessor in accessors) {
|
||||
if (accessor.isSetter && accessor.displayName == name) {
|
||||
if (result == null) {
|
||||
result = accessor;
|
||||
} else {
|
||||
throw new StateError('Class setter $name is not unique.');
|
||||
if (result != null) {
|
||||
fail('Not unique: $name');
|
||||
}
|
||||
result = accessor;
|
||||
}
|
||||
}
|
||||
}
|
||||
if (result == null) {
|
||||
fail('Not found class setter: $name');
|
||||
|
||||
for (var class_ in unitElement.types) {
|
||||
if (of != null && class_.name != of) {
|
||||
continue;
|
||||
}
|
||||
findIn(class_.accessors);
|
||||
}
|
||||
return result;
|
||||
|
||||
for (var mixin in unitElement.mixins) {
|
||||
if (of != null && mixin.name != of) {
|
||||
continue;
|
||||
}
|
||||
findIn(mixin.accessors);
|
||||
}
|
||||
|
||||
if (result != null) {
|
||||
return result;
|
||||
}
|
||||
fail('Not found: $name');
|
||||
}
|
||||
|
||||
FunctionElement topFunction(String name) {
|
||||
|
@ -310,7 +374,7 @@ class FindElement {
|
|||
return function;
|
||||
}
|
||||
}
|
||||
fail('Not found top-level function: $name');
|
||||
fail('Not found: $name');
|
||||
}
|
||||
|
||||
PropertyAccessorElement topGet(String name) {
|
||||
|
@ -327,34 +391,42 @@ class FindElement {
|
|||
return variable;
|
||||
}
|
||||
}
|
||||
fail('Not found top-level variable: $name');
|
||||
fail('Not found: $name');
|
||||
}
|
||||
|
||||
TypeParameterElement typeParameter(String name) {
|
||||
TypeParameterElement result;
|
||||
|
||||
void consider(TypeParameterElement candidate) {
|
||||
if (candidate.name == name) {
|
||||
if (result != null) {
|
||||
throw new StateError('Type parameter $name is not unique.');
|
||||
void findIn(List<TypeParameterElement> typeParameters) {
|
||||
for (var typeParameter in typeParameters) {
|
||||
if (typeParameter.name == name) {
|
||||
if (result != null) {
|
||||
fail('Not unique: $name');
|
||||
}
|
||||
result = typeParameter;
|
||||
}
|
||||
result = candidate;
|
||||
}
|
||||
}
|
||||
|
||||
for (var type in unitElement.functionTypeAliases) {
|
||||
type.typeParameters.forEach(consider);
|
||||
findIn(type.typeParameters);
|
||||
if (type is GenericTypeAliasElement) {
|
||||
type.function.typeParameters.forEach(consider);
|
||||
findIn(type.function.typeParameters);
|
||||
}
|
||||
}
|
||||
for (var type in unitElement.types) {
|
||||
type.typeParameters.forEach(consider);
|
||||
|
||||
for (var class_ in unitElement.types) {
|
||||
findIn(class_.typeParameters);
|
||||
}
|
||||
|
||||
for (var mixin in unitElement.mixins) {
|
||||
findIn(mixin.typeParameters);
|
||||
}
|
||||
|
||||
if (result != null) {
|
||||
return result;
|
||||
}
|
||||
fail('Not found type parameter: $name');
|
||||
fail('Not found: $name');
|
||||
}
|
||||
|
||||
ConstructorElement unnamedConstructor(String name) {
|
||||
|
|
|
@ -73,7 +73,7 @@ class B extends Object with A {
|
|||
var access = findNode.propertyAccess('foo = v; // ref');
|
||||
assertPropertyAccess(
|
||||
access,
|
||||
findElement.setter('foo', className: 'A'),
|
||||
findElement.setter('foo', of: 'A'),
|
||||
'int',
|
||||
);
|
||||
assertSuperExpression(access.target);
|
||||
|
@ -97,7 +97,7 @@ class B extends A {
|
|||
var access = findNode.propertyAccess('foo = v; // ref');
|
||||
assertPropertyAccess(
|
||||
access,
|
||||
findElement.setter('foo', className: 'A'),
|
||||
findElement.setter('foo', of: 'A'),
|
||||
'int',
|
||||
);
|
||||
assertSuperExpression(access.target);
|
||||
|
|
Loading…
Reference in a new issue