OLD | NEW |
(Empty) | |
| 1 // Copyright (c) 2014, the Dart project authors. Please see the AUTHORS file |
| 2 // for details. All rights reserved. Use of this source code is governed by a |
| 3 // BSD-style license that can be found in the LICENSE file. |
| 4 |
| 5 library engine.element_test; |
| 6 |
| 7 import 'package:analyzer/src/generated/ast.dart'; |
| 8 import 'package:analyzer/src/generated/element.dart'; |
| 9 import 'package:analyzer/src/generated/engine.dart' |
| 10 show AnalysisContext, AnalysisOptionsImpl; |
| 11 import 'package:analyzer/src/generated/java_core.dart'; |
| 12 import 'package:analyzer/src/generated/source_io.dart'; |
| 13 import 'package:analyzer/src/generated/testing/ast_factory.dart'; |
| 14 import 'package:analyzer/src/generated/testing/element_factory.dart'; |
| 15 import 'package:analyzer/src/generated/testing/test_type_provider.dart'; |
| 16 import 'package:unittest/unittest.dart'; |
| 17 |
| 18 import '../reflective_tests.dart'; |
| 19 import '../utils.dart'; |
| 20 import 'resolver_test.dart' show TestTypeProvider, AnalysisContextHelper; |
| 21 import 'test_support.dart'; |
| 22 |
| 23 main() { |
| 24 initializeTestEnvironment(); |
| 25 runReflectiveTests(ElementKindTest); |
| 26 runReflectiveTests(FieldElementImplTest); |
| 27 runReflectiveTests(FunctionTypeImplTest); |
| 28 runReflectiveTests(InterfaceTypeImplTest); |
| 29 runReflectiveTests(TypeParameterTypeImplTest); |
| 30 runReflectiveTests(VoidTypeImplTest); |
| 31 runReflectiveTests(ClassElementImplTest); |
| 32 runReflectiveTests(CompilationUnitElementImplTest); |
| 33 runReflectiveTests(ElementLocationImplTest); |
| 34 runReflectiveTests(ElementImplTest); |
| 35 runReflectiveTests(HtmlElementImplTest); |
| 36 runReflectiveTests(LibraryElementImplTest); |
| 37 runReflectiveTests(MethodElementImplTest); |
| 38 runReflectiveTests(MultiplyDefinedElementImplTest); |
| 39 runReflectiveTests(ParameterElementImplTest); |
| 40 } |
| 41 |
| 42 @reflectiveTest |
| 43 class ClassElementImplTest extends EngineTestCase { |
| 44 void test_computeNode_ClassDeclaration() { |
| 45 AnalysisContextHelper contextHelper = new AnalysisContextHelper(); |
| 46 AnalysisContext context = contextHelper.context; |
| 47 Source source = contextHelper.addSource( |
| 48 "/test.dart", |
| 49 r''' |
| 50 class A {} |
| 51 @deprecated class B {} |
| 52 enum C {C1, C2, C3} |
| 53 @deprecated enum D {D1, D2, D3}'''); |
| 54 // prepare CompilationUnitElement |
| 55 LibraryElement libraryElement = context.computeLibraryElement(source); |
| 56 CompilationUnitElement unitElement = libraryElement.definingCompilationUnit; |
| 57 // A |
| 58 { |
| 59 ClassElement elementA = unitElement.getType("A"); |
| 60 expect(elementA.isDeprecated, isFalse); |
| 61 expect(elementA.isEnum, isFalse); |
| 62 ClassDeclaration nodeA = elementA.computeNode(); |
| 63 expect(nodeA, isNotNull); |
| 64 expect(nodeA.name.name, "A"); |
| 65 expect(nodeA.element, same(elementA)); |
| 66 } |
| 67 // B |
| 68 { |
| 69 ClassElement elementB = unitElement.getType("B"); |
| 70 expect(elementB.isDeprecated, isTrue); |
| 71 expect(elementB.isEnum, isFalse); |
| 72 ClassDeclaration nodeB = elementB.computeNode(); |
| 73 expect(nodeB, isNotNull); |
| 74 expect(nodeB.name.name, "B"); |
| 75 expect(nodeB.element, same(elementB)); |
| 76 } |
| 77 // C |
| 78 { |
| 79 ClassElement elementC = unitElement.getEnum("C"); |
| 80 expect(elementC.isDeprecated, isFalse); |
| 81 expect(elementC.isEnum, isTrue); |
| 82 EnumDeclaration nodeC = elementC.computeNode(); |
| 83 expect(nodeC, isNotNull); |
| 84 expect(nodeC.name.name, "C"); |
| 85 expect(nodeC.element, same(elementC)); |
| 86 } |
| 87 // D |
| 88 { |
| 89 ClassElement elementD = unitElement.getEnum("D"); |
| 90 expect(elementD.isDeprecated, isTrue); |
| 91 expect(elementD.isEnum, isTrue); |
| 92 EnumDeclaration nodeC = elementD.computeNode(); |
| 93 expect(nodeC, isNotNull); |
| 94 expect(nodeC.name.name, "D"); |
| 95 expect(nodeC.element, same(elementD)); |
| 96 } |
| 97 } |
| 98 |
| 99 void test_computeNode_ClassTypeAlias() { |
| 100 AnalysisContextHelper contextHelper = new AnalysisContextHelper(); |
| 101 AnalysisContext context = contextHelper.context; |
| 102 Source source = contextHelper.addSource( |
| 103 "/test.dart", |
| 104 r''' |
| 105 abstract class A<K, V> = Object with MapMixin<K, V>; |
| 106 '''); |
| 107 // prepare CompilationUnitElement |
| 108 LibraryElement libraryElement = context.computeLibraryElement(source); |
| 109 CompilationUnitElement unitElement = libraryElement.definingCompilationUnit; |
| 110 // A |
| 111 { |
| 112 ClassElement elementA = unitElement.getType("A"); |
| 113 ClassTypeAlias nodeA = elementA.computeNode(); |
| 114 expect(nodeA, isNotNull); |
| 115 expect(nodeA.name.name, "A"); |
| 116 expect(nodeA.element, same(elementA)); |
| 117 } |
| 118 } |
| 119 |
| 120 void test_getAllSupertypes_interface() { |
| 121 ClassElement classA = ElementFactory.classElement2("A"); |
| 122 ClassElement classB = ElementFactory.classElement("B", classA.type); |
| 123 ClassElementImpl elementC = ElementFactory.classElement2("C"); |
| 124 InterfaceType typeObject = classA.supertype; |
| 125 InterfaceType typeA = classA.type; |
| 126 InterfaceType typeB = classB.type; |
| 127 InterfaceType typeC = elementC.type; |
| 128 elementC.interfaces = <InterfaceType>[typeB]; |
| 129 List<InterfaceType> supers = elementC.allSupertypes; |
| 130 List<InterfaceType> types = new List<InterfaceType>(); |
| 131 types.addAll(supers); |
| 132 expect(types.contains(typeA), isTrue); |
| 133 expect(types.contains(typeB), isTrue); |
| 134 expect(types.contains(typeObject), isTrue); |
| 135 expect(types.contains(typeC), isFalse); |
| 136 } |
| 137 |
| 138 void test_getAllSupertypes_mixins() { |
| 139 ClassElement classA = ElementFactory.classElement2("A"); |
| 140 ClassElement classB = ElementFactory.classElement("B", classA.type); |
| 141 ClassElementImpl classC = ElementFactory.classElement2("C"); |
| 142 InterfaceType typeObject = classA.supertype; |
| 143 InterfaceType typeA = classA.type; |
| 144 InterfaceType typeB = classB.type; |
| 145 InterfaceType typeC = classC.type; |
| 146 classC.mixins = <InterfaceType>[typeB]; |
| 147 List<InterfaceType> supers = classC.allSupertypes; |
| 148 List<InterfaceType> types = new List<InterfaceType>(); |
| 149 types.addAll(supers); |
| 150 expect(types.contains(typeA), isFalse); |
| 151 expect(types.contains(typeB), isTrue); |
| 152 expect(types.contains(typeObject), isTrue); |
| 153 expect(types.contains(typeC), isFalse); |
| 154 } |
| 155 |
| 156 void test_getAllSupertypes_recursive() { |
| 157 ClassElementImpl classA = ElementFactory.classElement2("A"); |
| 158 ClassElementImpl classB = ElementFactory.classElement("B", classA.type); |
| 159 classA.supertype = classB.type; |
| 160 List<InterfaceType> supers = classB.allSupertypes; |
| 161 expect(supers, hasLength(1)); |
| 162 } |
| 163 |
| 164 void test_getField() { |
| 165 ClassElementImpl classA = ElementFactory.classElement2("A"); |
| 166 String fieldName = "f"; |
| 167 FieldElementImpl field = |
| 168 ElementFactory.fieldElement(fieldName, false, false, false, null); |
| 169 classA.fields = <FieldElement>[field]; |
| 170 expect(classA.getField(fieldName), same(field)); |
| 171 expect(field.isEnumConstant, false); |
| 172 // no such field |
| 173 expect(classA.getField("noSuchField"), same(null)); |
| 174 } |
| 175 |
| 176 void test_getMethod_declared() { |
| 177 ClassElementImpl classA = ElementFactory.classElement2("A"); |
| 178 String methodName = "m"; |
| 179 MethodElement method = ElementFactory.methodElement(methodName, null); |
| 180 classA.methods = <MethodElement>[method]; |
| 181 expect(classA.getMethod(methodName), same(method)); |
| 182 } |
| 183 |
| 184 void test_getMethod_undeclared() { |
| 185 ClassElementImpl classA = ElementFactory.classElement2("A"); |
| 186 String methodName = "m"; |
| 187 MethodElement method = ElementFactory.methodElement(methodName, null); |
| 188 classA.methods = <MethodElement>[method]; |
| 189 expect(classA.getMethod("${methodName}x"), isNull); |
| 190 } |
| 191 |
| 192 void test_hasNonFinalField_false_const() { |
| 193 ClassElementImpl classA = ElementFactory.classElement2("A"); |
| 194 classA.fields = <FieldElement>[ |
| 195 ElementFactory.fieldElement("f", false, false, true, classA.type) |
| 196 ]; |
| 197 expect(classA.hasNonFinalField, isFalse); |
| 198 } |
| 199 |
| 200 void test_hasNonFinalField_false_final() { |
| 201 ClassElementImpl classA = ElementFactory.classElement2("A"); |
| 202 classA.fields = <FieldElement>[ |
| 203 ElementFactory.fieldElement("f", false, true, false, classA.type) |
| 204 ]; |
| 205 expect(classA.hasNonFinalField, isFalse); |
| 206 } |
| 207 |
| 208 void test_hasNonFinalField_false_recursive() { |
| 209 ClassElementImpl classA = ElementFactory.classElement2("A"); |
| 210 ClassElementImpl classB = ElementFactory.classElement("B", classA.type); |
| 211 classA.supertype = classB.type; |
| 212 expect(classA.hasNonFinalField, isFalse); |
| 213 } |
| 214 |
| 215 void test_hasNonFinalField_true_immediate() { |
| 216 ClassElementImpl classA = ElementFactory.classElement2("A"); |
| 217 classA.fields = <FieldElement>[ |
| 218 ElementFactory.fieldElement("f", false, false, false, classA.type) |
| 219 ]; |
| 220 expect(classA.hasNonFinalField, isTrue); |
| 221 } |
| 222 |
| 223 void test_hasNonFinalField_true_inherited() { |
| 224 ClassElementImpl classA = ElementFactory.classElement2("A"); |
| 225 ClassElementImpl classB = ElementFactory.classElement("B", classA.type); |
| 226 classA.fields = <FieldElement>[ |
| 227 ElementFactory.fieldElement("f", false, false, false, classA.type) |
| 228 ]; |
| 229 expect(classB.hasNonFinalField, isTrue); |
| 230 } |
| 231 |
| 232 void test_hasStaticMember_false_empty() { |
| 233 ClassElementImpl classA = ElementFactory.classElement2("A"); |
| 234 // no members |
| 235 expect(classA.hasStaticMember, isFalse); |
| 236 } |
| 237 |
| 238 void test_hasStaticMember_false_instanceMethod() { |
| 239 ClassElementImpl classA = ElementFactory.classElement2("A"); |
| 240 MethodElement method = ElementFactory.methodElement("foo", null); |
| 241 classA.methods = <MethodElement>[method]; |
| 242 expect(classA.hasStaticMember, isFalse); |
| 243 } |
| 244 |
| 245 void test_hasStaticMember_instanceGetter() { |
| 246 ClassElementImpl classA = ElementFactory.classElement2("A"); |
| 247 PropertyAccessorElement getter = |
| 248 ElementFactory.getterElement("foo", false, null); |
| 249 classA.accessors = <PropertyAccessorElement>[getter]; |
| 250 expect(classA.hasStaticMember, isFalse); |
| 251 } |
| 252 |
| 253 void test_hasStaticMember_true_getter() { |
| 254 ClassElementImpl classA = ElementFactory.classElement2("A"); |
| 255 PropertyAccessorElementImpl getter = |
| 256 ElementFactory.getterElement("foo", false, null); |
| 257 classA.accessors = <PropertyAccessorElement>[getter]; |
| 258 // "foo" is static |
| 259 getter.static = true; |
| 260 expect(classA.hasStaticMember, isTrue); |
| 261 } |
| 262 |
| 263 void test_hasStaticMember_true_method() { |
| 264 ClassElementImpl classA = ElementFactory.classElement2("A"); |
| 265 MethodElementImpl method = ElementFactory.methodElement("foo", null); |
| 266 classA.methods = <MethodElement>[method]; |
| 267 // "foo" is static |
| 268 method.static = true; |
| 269 expect(classA.hasStaticMember, isTrue); |
| 270 } |
| 271 |
| 272 void test_hasStaticMember_true_setter() { |
| 273 ClassElementImpl classA = ElementFactory.classElement2("A"); |
| 274 PropertyAccessorElementImpl setter = |
| 275 ElementFactory.setterElement("foo", false, null); |
| 276 classA.accessors = <PropertyAccessorElement>[setter]; |
| 277 // "foo" is static |
| 278 setter.static = true; |
| 279 expect(classA.hasStaticMember, isTrue); |
| 280 } |
| 281 |
| 282 void test_isEnum() { |
| 283 String firstConst = "A"; |
| 284 String secondConst = "B"; |
| 285 ClassElementImpl enumE = ElementFactory.enumElement( |
| 286 new TestTypeProvider(), "E", [firstConst, secondConst]); |
| 287 |
| 288 // E is an enum |
| 289 expect(enumE.isEnum, true); |
| 290 |
| 291 // A and B are static members |
| 292 expect(enumE.getField(firstConst).isEnumConstant, true); |
| 293 expect(enumE.getField(secondConst).isEnumConstant, true); |
| 294 } |
| 295 |
| 296 void test_lookUpConcreteMethod_declared() { |
| 297 // class A { |
| 298 // m() {} |
| 299 // } |
| 300 LibraryElementImpl library = |
| 301 ElementFactory.library(createAnalysisContext(), "lib"); |
| 302 ClassElementImpl classA = ElementFactory.classElement2("A"); |
| 303 String methodName = "m"; |
| 304 MethodElement method = ElementFactory.methodElement(methodName, null); |
| 305 classA.methods = <MethodElement>[method]; |
| 306 (library.definingCompilationUnit as CompilationUnitElementImpl).types = |
| 307 <ClassElement>[classA]; |
| 308 expect(classA.lookUpConcreteMethod(methodName, library), same(method)); |
| 309 } |
| 310 |
| 311 void test_lookUpConcreteMethod_declaredAbstract() { |
| 312 // class A { |
| 313 // m(); |
| 314 // } |
| 315 LibraryElementImpl library = |
| 316 ElementFactory.library(createAnalysisContext(), "lib"); |
| 317 ClassElementImpl classA = ElementFactory.classElement2("A"); |
| 318 String methodName = "m"; |
| 319 MethodElementImpl method = ElementFactory.methodElement(methodName, null); |
| 320 method.abstract = true; |
| 321 classA.methods = <MethodElement>[method]; |
| 322 (library.definingCompilationUnit as CompilationUnitElementImpl).types = |
| 323 <ClassElement>[classA]; |
| 324 expect(classA.lookUpConcreteMethod(methodName, library), isNull); |
| 325 } |
| 326 |
| 327 void test_lookUpConcreteMethod_declaredAbstractAndInherited() { |
| 328 // class A { |
| 329 // m() {} |
| 330 // } |
| 331 // class B extends A { |
| 332 // m(); |
| 333 // } |
| 334 LibraryElementImpl library = |
| 335 ElementFactory.library(createAnalysisContext(), "lib"); |
| 336 ClassElementImpl classA = ElementFactory.classElement2("A"); |
| 337 String methodName = "m"; |
| 338 MethodElement inheritedMethod = |
| 339 ElementFactory.methodElement(methodName, null); |
| 340 classA.methods = <MethodElement>[inheritedMethod]; |
| 341 ClassElementImpl classB = ElementFactory.classElement("B", classA.type); |
| 342 MethodElementImpl method = ElementFactory.methodElement(methodName, null); |
| 343 method.abstract = true; |
| 344 classB.methods = <MethodElement>[method]; |
| 345 (library.definingCompilationUnit as CompilationUnitElementImpl).types = |
| 346 <ClassElement>[classA, classB]; |
| 347 expect(classB.lookUpConcreteMethod(methodName, library), |
| 348 same(inheritedMethod)); |
| 349 } |
| 350 |
| 351 void test_lookUpConcreteMethod_declaredAndInherited() { |
| 352 // class A { |
| 353 // m() {} |
| 354 // } |
| 355 // class B extends A { |
| 356 // m() {} |
| 357 // } |
| 358 LibraryElementImpl library = |
| 359 ElementFactory.library(createAnalysisContext(), "lib"); |
| 360 ClassElementImpl classA = ElementFactory.classElement2("A"); |
| 361 String methodName = "m"; |
| 362 MethodElement inheritedMethod = |
| 363 ElementFactory.methodElement(methodName, null); |
| 364 classA.methods = <MethodElement>[inheritedMethod]; |
| 365 ClassElementImpl classB = ElementFactory.classElement("B", classA.type); |
| 366 MethodElement method = ElementFactory.methodElement(methodName, null); |
| 367 classB.methods = <MethodElement>[method]; |
| 368 (library.definingCompilationUnit as CompilationUnitElementImpl).types = |
| 369 <ClassElement>[classA, classB]; |
| 370 expect(classB.lookUpConcreteMethod(methodName, library), same(method)); |
| 371 } |
| 372 |
| 373 void test_lookUpConcreteMethod_declaredAndInheritedAbstract() { |
| 374 // abstract class A { |
| 375 // m(); |
| 376 // } |
| 377 // class B extends A { |
| 378 // m() {} |
| 379 // } |
| 380 LibraryElementImpl library = |
| 381 ElementFactory.library(createAnalysisContext(), "lib"); |
| 382 ClassElementImpl classA = ElementFactory.classElement2("A"); |
| 383 classA.abstract = true; |
| 384 String methodName = "m"; |
| 385 MethodElementImpl inheritedMethod = |
| 386 ElementFactory.methodElement(methodName, null); |
| 387 inheritedMethod.abstract = true; |
| 388 classA.methods = <MethodElement>[inheritedMethod]; |
| 389 ClassElementImpl classB = ElementFactory.classElement("B", classA.type); |
| 390 MethodElement method = ElementFactory.methodElement(methodName, null); |
| 391 classB.methods = <MethodElement>[method]; |
| 392 (library.definingCompilationUnit as CompilationUnitElementImpl).types = |
| 393 <ClassElement>[classA, classB]; |
| 394 expect(classB.lookUpConcreteMethod(methodName, library), same(method)); |
| 395 } |
| 396 |
| 397 void test_lookUpConcreteMethod_inherited() { |
| 398 // class A { |
| 399 // m() {} |
| 400 // } |
| 401 // class B extends A { |
| 402 // } |
| 403 LibraryElementImpl library = |
| 404 ElementFactory.library(createAnalysisContext(), "lib"); |
| 405 ClassElementImpl classA = ElementFactory.classElement2("A"); |
| 406 String methodName = "m"; |
| 407 MethodElement inheritedMethod = |
| 408 ElementFactory.methodElement(methodName, null); |
| 409 classA.methods = <MethodElement>[inheritedMethod]; |
| 410 ClassElementImpl classB = ElementFactory.classElement("B", classA.type); |
| 411 (library.definingCompilationUnit as CompilationUnitElementImpl).types = |
| 412 <ClassElement>[classA, classB]; |
| 413 expect(classB.lookUpConcreteMethod(methodName, library), |
| 414 same(inheritedMethod)); |
| 415 } |
| 416 |
| 417 void test_lookUpConcreteMethod_undeclared() { |
| 418 // class A { |
| 419 // } |
| 420 LibraryElementImpl library = |
| 421 ElementFactory.library(createAnalysisContext(), "lib"); |
| 422 ClassElementImpl classA = ElementFactory.classElement2("A"); |
| 423 (library.definingCompilationUnit as CompilationUnitElementImpl).types = |
| 424 <ClassElement>[classA]; |
| 425 expect(classA.lookUpConcreteMethod("m", library), isNull); |
| 426 } |
| 427 |
| 428 void test_lookUpGetter_declared() { |
| 429 // class A { |
| 430 // get g {} |
| 431 // } |
| 432 LibraryElementImpl library = |
| 433 ElementFactory.library(createAnalysisContext(), "lib"); |
| 434 ClassElementImpl classA = ElementFactory.classElement2("A"); |
| 435 String getterName = "g"; |
| 436 PropertyAccessorElement getter = |
| 437 ElementFactory.getterElement(getterName, false, null); |
| 438 classA.accessors = <PropertyAccessorElement>[getter]; |
| 439 (library.definingCompilationUnit as CompilationUnitElementImpl).types = |
| 440 <ClassElement>[classA]; |
| 441 expect(classA.lookUpGetter(getterName, library), same(getter)); |
| 442 } |
| 443 |
| 444 void test_lookUpGetter_inherited() { |
| 445 // class A { |
| 446 // get g {} |
| 447 // } |
| 448 // class B extends A { |
| 449 // } |
| 450 LibraryElementImpl library = |
| 451 ElementFactory.library(createAnalysisContext(), "lib"); |
| 452 ClassElementImpl classA = ElementFactory.classElement2("A"); |
| 453 String getterName = "g"; |
| 454 PropertyAccessorElement getter = |
| 455 ElementFactory.getterElement(getterName, false, null); |
| 456 classA.accessors = <PropertyAccessorElement>[getter]; |
| 457 ClassElementImpl classB = ElementFactory.classElement("B", classA.type); |
| 458 (library.definingCompilationUnit as CompilationUnitElementImpl).types = |
| 459 <ClassElement>[classA, classB]; |
| 460 expect(classB.lookUpGetter(getterName, library), same(getter)); |
| 461 } |
| 462 |
| 463 void test_lookUpGetter_undeclared() { |
| 464 // class A { |
| 465 // } |
| 466 LibraryElementImpl library = |
| 467 ElementFactory.library(createAnalysisContext(), "lib"); |
| 468 ClassElementImpl classA = ElementFactory.classElement2("A"); |
| 469 (library.definingCompilationUnit as CompilationUnitElementImpl).types = |
| 470 <ClassElement>[classA]; |
| 471 expect(classA.lookUpGetter("g", library), isNull); |
| 472 } |
| 473 |
| 474 void test_lookUpGetter_undeclared_recursive() { |
| 475 // class A extends B { |
| 476 // } |
| 477 // class B extends A { |
| 478 // } |
| 479 LibraryElementImpl library = |
| 480 ElementFactory.library(createAnalysisContext(), "lib"); |
| 481 ClassElementImpl classA = ElementFactory.classElement2("A"); |
| 482 ClassElementImpl classB = ElementFactory.classElement("B", classA.type); |
| 483 classA.supertype = classB.type; |
| 484 (library.definingCompilationUnit as CompilationUnitElementImpl).types = |
| 485 <ClassElement>[classA, classB]; |
| 486 expect(classA.lookUpGetter("g", library), isNull); |
| 487 } |
| 488 |
| 489 void test_lookUpInheritedConcreteGetter_declared() { |
| 490 // class A { |
| 491 // get g {} |
| 492 // } |
| 493 LibraryElementImpl library = |
| 494 ElementFactory.library(createAnalysisContext(), "lib"); |
| 495 ClassElementImpl classA = ElementFactory.classElement2("A"); |
| 496 String getterName = "g"; |
| 497 PropertyAccessorElement getter = |
| 498 ElementFactory.getterElement(getterName, false, null); |
| 499 classA.accessors = <PropertyAccessorElement>[getter]; |
| 500 (library.definingCompilationUnit as CompilationUnitElementImpl).types = |
| 501 <ClassElement>[classA]; |
| 502 expect(classA.lookUpInheritedConcreteGetter(getterName, library), isNull); |
| 503 } |
| 504 |
| 505 void test_lookUpInheritedConcreteGetter_inherited() { |
| 506 // class A { |
| 507 // get g {} |
| 508 // } |
| 509 // class B extends A { |
| 510 // } |
| 511 LibraryElementImpl library = |
| 512 ElementFactory.library(createAnalysisContext(), "lib"); |
| 513 ClassElementImpl classA = ElementFactory.classElement2("A"); |
| 514 String getterName = "g"; |
| 515 PropertyAccessorElement inheritedGetter = |
| 516 ElementFactory.getterElement(getterName, false, null); |
| 517 classA.accessors = <PropertyAccessorElement>[inheritedGetter]; |
| 518 ClassElementImpl classB = ElementFactory.classElement("B", classA.type); |
| 519 (library.definingCompilationUnit as CompilationUnitElementImpl).types = |
| 520 <ClassElement>[classA, classB]; |
| 521 expect(classB.lookUpInheritedConcreteGetter(getterName, library), |
| 522 same(inheritedGetter)); |
| 523 } |
| 524 |
| 525 void test_lookUpInheritedConcreteGetter_undeclared() { |
| 526 // class A { |
| 527 // } |
| 528 LibraryElementImpl library = |
| 529 ElementFactory.library(createAnalysisContext(), "lib"); |
| 530 ClassElementImpl classA = ElementFactory.classElement2("A"); |
| 531 (library.definingCompilationUnit as CompilationUnitElementImpl).types = |
| 532 <ClassElement>[classA]; |
| 533 expect(classA.lookUpInheritedConcreteGetter("g", library), isNull); |
| 534 } |
| 535 |
| 536 void test_lookUpInheritedConcreteGetter_undeclared_recursive() { |
| 537 // class A extends B { |
| 538 // } |
| 539 // class B extends A { |
| 540 // } |
| 541 LibraryElementImpl library = |
| 542 ElementFactory.library(createAnalysisContext(), "lib"); |
| 543 ClassElementImpl classA = ElementFactory.classElement2("A"); |
| 544 ClassElementImpl classB = ElementFactory.classElement("B", classA.type); |
| 545 classA.supertype = classB.type; |
| 546 (library.definingCompilationUnit as CompilationUnitElementImpl).types = |
| 547 <ClassElement>[classA, classB]; |
| 548 expect(classA.lookUpInheritedConcreteGetter("g", library), isNull); |
| 549 } |
| 550 |
| 551 void test_lookUpInheritedConcreteMethod_declared() { |
| 552 // class A { |
| 553 // m() {} |
| 554 // } |
| 555 LibraryElementImpl library = |
| 556 ElementFactory.library(createAnalysisContext(), "lib"); |
| 557 ClassElementImpl classA = ElementFactory.classElement2("A"); |
| 558 String methodName = "m"; |
| 559 MethodElement method = ElementFactory.methodElement(methodName, null); |
| 560 classA.methods = <MethodElement>[method]; |
| 561 (library.definingCompilationUnit as CompilationUnitElementImpl).types = |
| 562 <ClassElement>[classA]; |
| 563 expect(classA.lookUpInheritedConcreteMethod(methodName, library), isNull); |
| 564 } |
| 565 |
| 566 void test_lookUpInheritedConcreteMethod_declaredAbstractAndInherited() { |
| 567 // class A { |
| 568 // m() {} |
| 569 // } |
| 570 // class B extends A { |
| 571 // m(); |
| 572 // } |
| 573 LibraryElementImpl library = |
| 574 ElementFactory.library(createAnalysisContext(), "lib"); |
| 575 ClassElementImpl classA = ElementFactory.classElement2("A"); |
| 576 String methodName = "m"; |
| 577 MethodElement inheritedMethod = |
| 578 ElementFactory.methodElement(methodName, null); |
| 579 classA.methods = <MethodElement>[inheritedMethod]; |
| 580 ClassElementImpl classB = ElementFactory.classElement("B", classA.type); |
| 581 MethodElementImpl method = ElementFactory.methodElement(methodName, null); |
| 582 method.abstract = true; |
| 583 classB.methods = <MethodElement>[method]; |
| 584 (library.definingCompilationUnit as CompilationUnitElementImpl).types = |
| 585 <ClassElement>[classA, classB]; |
| 586 expect(classB.lookUpInheritedConcreteMethod(methodName, library), |
| 587 same(inheritedMethod)); |
| 588 } |
| 589 |
| 590 void test_lookUpInheritedConcreteMethod_declaredAndInherited() { |
| 591 // class A { |
| 592 // m() {} |
| 593 // } |
| 594 // class B extends A { |
| 595 // m() {} |
| 596 // } |
| 597 LibraryElementImpl library = |
| 598 ElementFactory.library(createAnalysisContext(), "lib"); |
| 599 ClassElementImpl classA = ElementFactory.classElement2("A"); |
| 600 String methodName = "m"; |
| 601 MethodElement inheritedMethod = |
| 602 ElementFactory.methodElement(methodName, null); |
| 603 classA.methods = <MethodElement>[inheritedMethod]; |
| 604 ClassElementImpl classB = ElementFactory.classElement("B", classA.type); |
| 605 MethodElement method = ElementFactory.methodElement(methodName, null); |
| 606 classB.methods = <MethodElement>[method]; |
| 607 (library.definingCompilationUnit as CompilationUnitElementImpl).types = |
| 608 <ClassElement>[classA, classB]; |
| 609 expect(classB.lookUpInheritedConcreteMethod(methodName, library), |
| 610 same(inheritedMethod)); |
| 611 } |
| 612 |
| 613 void test_lookUpInheritedConcreteMethod_declaredAndInheritedAbstract() { |
| 614 // abstract class A { |
| 615 // m(); |
| 616 // } |
| 617 // class B extends A { |
| 618 // m() {} |
| 619 // } |
| 620 LibraryElementImpl library = |
| 621 ElementFactory.library(createAnalysisContext(), "lib"); |
| 622 ClassElementImpl classA = ElementFactory.classElement2("A"); |
| 623 classA.abstract = true; |
| 624 String methodName = "m"; |
| 625 MethodElementImpl inheritedMethod = |
| 626 ElementFactory.methodElement(methodName, null); |
| 627 inheritedMethod.abstract = true; |
| 628 classA.methods = <MethodElement>[inheritedMethod]; |
| 629 ClassElementImpl classB = ElementFactory.classElement("B", classA.type); |
| 630 MethodElement method = ElementFactory.methodElement(methodName, null); |
| 631 classB.methods = <MethodElement>[method]; |
| 632 (library.definingCompilationUnit as CompilationUnitElementImpl).types = |
| 633 <ClassElement>[classA, classB]; |
| 634 expect(classB.lookUpInheritedConcreteMethod(methodName, library), isNull); |
| 635 } |
| 636 |
| 637 void test_lookUpInheritedConcreteMethod_declaredAndInheritedWithAbstractBetwee
n() { |
| 638 // class A { |
| 639 // m() {} |
| 640 // } |
| 641 // class B extends A { |
| 642 // m(); |
| 643 // } |
| 644 // class C extends B { |
| 645 // m() {} |
| 646 // } |
| 647 LibraryElementImpl library = |
| 648 ElementFactory.library(createAnalysisContext(), "lib"); |
| 649 ClassElementImpl classA = ElementFactory.classElement2("A"); |
| 650 String methodName = "m"; |
| 651 MethodElement inheritedMethod = |
| 652 ElementFactory.methodElement(methodName, null); |
| 653 classA.methods = <MethodElement>[inheritedMethod]; |
| 654 ClassElementImpl classB = ElementFactory.classElement("B", classA.type); |
| 655 MethodElementImpl abstractMethod = |
| 656 ElementFactory.methodElement(methodName, null); |
| 657 abstractMethod.abstract = true; |
| 658 classB.methods = <MethodElement>[abstractMethod]; |
| 659 ClassElementImpl classC = ElementFactory.classElement("C", classB.type); |
| 660 MethodElementImpl method = ElementFactory.methodElement(methodName, null); |
| 661 classC.methods = <MethodElement>[method]; |
| 662 (library.definingCompilationUnit as CompilationUnitElementImpl).types = |
| 663 <ClassElement>[classA, classB, classC]; |
| 664 expect(classC.lookUpInheritedConcreteMethod(methodName, library), |
| 665 same(inheritedMethod)); |
| 666 } |
| 667 |
| 668 void test_lookUpInheritedConcreteMethod_inherited() { |
| 669 // class A { |
| 670 // m() {} |
| 671 // } |
| 672 // class B extends A { |
| 673 // } |
| 674 LibraryElementImpl library = |
| 675 ElementFactory.library(createAnalysisContext(), "lib"); |
| 676 ClassElementImpl classA = ElementFactory.classElement2("A"); |
| 677 String methodName = "m"; |
| 678 MethodElement inheritedMethod = |
| 679 ElementFactory.methodElement(methodName, null); |
| 680 classA.methods = <MethodElement>[inheritedMethod]; |
| 681 ClassElementImpl classB = ElementFactory.classElement("B", classA.type); |
| 682 (library.definingCompilationUnit as CompilationUnitElementImpl).types = |
| 683 <ClassElement>[classA, classB]; |
| 684 expect(classB.lookUpInheritedConcreteMethod(methodName, library), |
| 685 same(inheritedMethod)); |
| 686 } |
| 687 |
| 688 void test_lookUpInheritedConcreteMethod_undeclared() { |
| 689 // class A { |
| 690 // } |
| 691 LibraryElementImpl library = |
| 692 ElementFactory.library(createAnalysisContext(), "lib"); |
| 693 ClassElementImpl classA = ElementFactory.classElement2("A"); |
| 694 (library.definingCompilationUnit as CompilationUnitElementImpl).types = |
| 695 <ClassElement>[classA]; |
| 696 expect(classA.lookUpInheritedConcreteMethod("m", library), isNull); |
| 697 } |
| 698 |
| 699 void test_lookUpInheritedConcreteSetter_declared() { |
| 700 // class A { |
| 701 // set g(x) {} |
| 702 // } |
| 703 LibraryElementImpl library = |
| 704 ElementFactory.library(createAnalysisContext(), "lib"); |
| 705 ClassElementImpl classA = ElementFactory.classElement2("A"); |
| 706 String setterName = "s"; |
| 707 PropertyAccessorElement setter = |
| 708 ElementFactory.setterElement(setterName, false, null); |
| 709 classA.accessors = <PropertyAccessorElement>[setter]; |
| 710 (library.definingCompilationUnit as CompilationUnitElementImpl).types = |
| 711 <ClassElement>[classA]; |
| 712 expect(classA.lookUpInheritedConcreteSetter(setterName, library), isNull); |
| 713 } |
| 714 |
| 715 void test_lookUpInheritedConcreteSetter_inherited() { |
| 716 // class A { |
| 717 // set g(x) {} |
| 718 // } |
| 719 // class B extends A { |
| 720 // } |
| 721 LibraryElementImpl library = |
| 722 ElementFactory.library(createAnalysisContext(), "lib"); |
| 723 ClassElementImpl classA = ElementFactory.classElement2("A"); |
| 724 String setterName = "s"; |
| 725 PropertyAccessorElement setter = |
| 726 ElementFactory.setterElement(setterName, false, null); |
| 727 classA.accessors = <PropertyAccessorElement>[setter]; |
| 728 ClassElementImpl classB = ElementFactory.classElement("B", classA.type); |
| 729 (library.definingCompilationUnit as CompilationUnitElementImpl).types = |
| 730 <ClassElement>[classA, classB]; |
| 731 expect(classB.lookUpInheritedConcreteSetter(setterName, library), |
| 732 same(setter)); |
| 733 } |
| 734 |
| 735 void test_lookUpInheritedConcreteSetter_undeclared() { |
| 736 // class A { |
| 737 // } |
| 738 LibraryElementImpl library = |
| 739 ElementFactory.library(createAnalysisContext(), "lib"); |
| 740 ClassElementImpl classA = ElementFactory.classElement2("A"); |
| 741 (library.definingCompilationUnit as CompilationUnitElementImpl).types = |
| 742 <ClassElement>[classA]; |
| 743 expect(classA.lookUpInheritedConcreteSetter("s", library), isNull); |
| 744 } |
| 745 |
| 746 void test_lookUpInheritedConcreteSetter_undeclared_recursive() { |
| 747 // class A extends B { |
| 748 // } |
| 749 // class B extends A { |
| 750 // } |
| 751 LibraryElementImpl library = |
| 752 ElementFactory.library(createAnalysisContext(), "lib"); |
| 753 ClassElementImpl classA = ElementFactory.classElement2("A"); |
| 754 ClassElementImpl classB = ElementFactory.classElement("B", classA.type); |
| 755 classA.supertype = classB.type; |
| 756 (library.definingCompilationUnit as CompilationUnitElementImpl).types = |
| 757 <ClassElement>[classA, classB]; |
| 758 expect(classA.lookUpInheritedConcreteSetter("s", library), isNull); |
| 759 } |
| 760 |
| 761 void test_lookUpInheritedMethod_declared() { |
| 762 // class A { |
| 763 // m() {} |
| 764 // } |
| 765 LibraryElementImpl library = |
| 766 ElementFactory.library(createAnalysisContext(), "lib"); |
| 767 ClassElementImpl classA = ElementFactory.classElement2("A"); |
| 768 String methodName = "m"; |
| 769 MethodElement method = ElementFactory.methodElement(methodName, null); |
| 770 classA.methods = <MethodElement>[method]; |
| 771 (library.definingCompilationUnit as CompilationUnitElementImpl).types = |
| 772 <ClassElement>[classA]; |
| 773 expect(classA.lookUpInheritedMethod(methodName, library), isNull); |
| 774 } |
| 775 |
| 776 void test_lookUpInheritedMethod_declaredAndInherited() { |
| 777 // class A { |
| 778 // m() {} |
| 779 // } |
| 780 // class B extends A { |
| 781 // m() {} |
| 782 // } |
| 783 LibraryElementImpl library = |
| 784 ElementFactory.library(createAnalysisContext(), "lib"); |
| 785 ClassElementImpl classA = ElementFactory.classElement2("A"); |
| 786 String methodName = "m"; |
| 787 MethodElement inheritedMethod = |
| 788 ElementFactory.methodElement(methodName, null); |
| 789 classA.methods = <MethodElement>[inheritedMethod]; |
| 790 ClassElementImpl classB = ElementFactory.classElement("B", classA.type); |
| 791 MethodElement method = ElementFactory.methodElement(methodName, null); |
| 792 classB.methods = <MethodElement>[method]; |
| 793 (library.definingCompilationUnit as CompilationUnitElementImpl).types = |
| 794 <ClassElement>[classA, classB]; |
| 795 expect(classB.lookUpInheritedMethod(methodName, library), |
| 796 same(inheritedMethod)); |
| 797 } |
| 798 |
| 799 void test_lookUpInheritedMethod_inherited() { |
| 800 // class A { |
| 801 // m() {} |
| 802 // } |
| 803 // class B extends A { |
| 804 // } |
| 805 LibraryElementImpl library = |
| 806 ElementFactory.library(createAnalysisContext(), "lib"); |
| 807 ClassElementImpl classA = ElementFactory.classElement2("A"); |
| 808 String methodName = "m"; |
| 809 MethodElement inheritedMethod = |
| 810 ElementFactory.methodElement(methodName, null); |
| 811 classA.methods = <MethodElement>[inheritedMethod]; |
| 812 ClassElementImpl classB = ElementFactory.classElement("B", classA.type); |
| 813 (library.definingCompilationUnit as CompilationUnitElementImpl).types = |
| 814 <ClassElement>[classA, classB]; |
| 815 expect(classB.lookUpInheritedMethod(methodName, library), |
| 816 same(inheritedMethod)); |
| 817 } |
| 818 |
| 819 void test_lookUpInheritedMethod_undeclared() { |
| 820 // class A { |
| 821 // } |
| 822 LibraryElementImpl library = |
| 823 ElementFactory.library(createAnalysisContext(), "lib"); |
| 824 ClassElementImpl classA = ElementFactory.classElement2("A"); |
| 825 (library.definingCompilationUnit as CompilationUnitElementImpl).types = |
| 826 <ClassElement>[classA]; |
| 827 expect(classA.lookUpInheritedMethod("m", library), isNull); |
| 828 } |
| 829 |
| 830 void test_lookUpMethod_declared() { |
| 831 LibraryElementImpl library = |
| 832 ElementFactory.library(createAnalysisContext(), "lib"); |
| 833 ClassElementImpl classA = ElementFactory.classElement2("A"); |
| 834 String methodName = "m"; |
| 835 MethodElement method = ElementFactory.methodElement(methodName, null); |
| 836 classA.methods = <MethodElement>[method]; |
| 837 (library.definingCompilationUnit as CompilationUnitElementImpl).types = |
| 838 <ClassElement>[classA]; |
| 839 expect(classA.lookUpMethod(methodName, library), same(method)); |
| 840 } |
| 841 |
| 842 void test_lookUpMethod_inherited() { |
| 843 LibraryElementImpl library = |
| 844 ElementFactory.library(createAnalysisContext(), "lib"); |
| 845 ClassElementImpl classA = ElementFactory.classElement2("A"); |
| 846 String methodName = "m"; |
| 847 MethodElement method = ElementFactory.methodElement(methodName, null); |
| 848 classA.methods = <MethodElement>[method]; |
| 849 ClassElementImpl classB = ElementFactory.classElement("B", classA.type); |
| 850 (library.definingCompilationUnit as CompilationUnitElementImpl).types = |
| 851 <ClassElement>[classA, classB]; |
| 852 expect(classB.lookUpMethod(methodName, library), same(method)); |
| 853 } |
| 854 |
| 855 void test_lookUpMethod_undeclared() { |
| 856 LibraryElementImpl library = |
| 857 ElementFactory.library(createAnalysisContext(), "lib"); |
| 858 ClassElementImpl classA = ElementFactory.classElement2("A"); |
| 859 (library.definingCompilationUnit as CompilationUnitElementImpl).types = |
| 860 <ClassElement>[classA]; |
| 861 expect(classA.lookUpMethod("m", library), isNull); |
| 862 } |
| 863 |
| 864 void test_lookUpMethod_undeclared_recursive() { |
| 865 LibraryElementImpl library = |
| 866 ElementFactory.library(createAnalysisContext(), "lib"); |
| 867 ClassElementImpl classA = ElementFactory.classElement2("A"); |
| 868 ClassElementImpl classB = ElementFactory.classElement("B", classA.type); |
| 869 classA.supertype = classB.type; |
| 870 (library.definingCompilationUnit as CompilationUnitElementImpl).types = |
| 871 <ClassElement>[classA, classB]; |
| 872 expect(classA.lookUpMethod("m", library), isNull); |
| 873 } |
| 874 |
| 875 void test_lookUpSetter_declared() { |
| 876 // class A { |
| 877 // set g(x) {} |
| 878 // } |
| 879 LibraryElementImpl library = |
| 880 ElementFactory.library(createAnalysisContext(), "lib"); |
| 881 ClassElementImpl classA = ElementFactory.classElement2("A"); |
| 882 String setterName = "s"; |
| 883 PropertyAccessorElement setter = |
| 884 ElementFactory.setterElement(setterName, false, null); |
| 885 classA.accessors = <PropertyAccessorElement>[setter]; |
| 886 (library.definingCompilationUnit as CompilationUnitElementImpl).types = |
| 887 <ClassElement>[classA]; |
| 888 expect(classA.lookUpSetter(setterName, library), same(setter)); |
| 889 } |
| 890 |
| 891 void test_lookUpSetter_inherited() { |
| 892 // class A { |
| 893 // set g(x) {} |
| 894 // } |
| 895 // class B extends A { |
| 896 // } |
| 897 LibraryElementImpl library = |
| 898 ElementFactory.library(createAnalysisContext(), "lib"); |
| 899 ClassElementImpl classA = ElementFactory.classElement2("A"); |
| 900 String setterName = "s"; |
| 901 PropertyAccessorElement setter = |
| 902 ElementFactory.setterElement(setterName, false, null); |
| 903 classA.accessors = <PropertyAccessorElement>[setter]; |
| 904 ClassElementImpl classB = ElementFactory.classElement("B", classA.type); |
| 905 (library.definingCompilationUnit as CompilationUnitElementImpl).types = |
| 906 <ClassElement>[classA, classB]; |
| 907 expect(classB.lookUpSetter(setterName, library), same(setter)); |
| 908 } |
| 909 |
| 910 void test_lookUpSetter_undeclared() { |
| 911 // class A { |
| 912 // } |
| 913 LibraryElementImpl library = |
| 914 ElementFactory.library(createAnalysisContext(), "lib"); |
| 915 ClassElementImpl classA = ElementFactory.classElement2("A"); |
| 916 (library.definingCompilationUnit as CompilationUnitElementImpl).types = |
| 917 <ClassElement>[classA]; |
| 918 expect(classA.lookUpSetter("s", library), isNull); |
| 919 } |
| 920 |
| 921 void test_lookUpSetter_undeclared_recursive() { |
| 922 // class A extends B { |
| 923 // } |
| 924 // class B extends A { |
| 925 // } |
| 926 LibraryElementImpl library = |
| 927 ElementFactory.library(createAnalysisContext(), "lib"); |
| 928 ClassElementImpl classA = ElementFactory.classElement2("A"); |
| 929 ClassElementImpl classB = ElementFactory.classElement("B", classA.type); |
| 930 classA.supertype = classB.type; |
| 931 (library.definingCompilationUnit as CompilationUnitElementImpl).types = |
| 932 <ClassElement>[classA, classB]; |
| 933 expect(classA.lookUpSetter("s", library), isNull); |
| 934 } |
| 935 } |
| 936 |
| 937 @reflectiveTest |
| 938 class CompilationUnitElementImplTest extends EngineTestCase { |
| 939 void test_getElementAt() { |
| 940 AnalysisContextHelper contextHelper = new AnalysisContextHelper(); |
| 941 AnalysisContext context = contextHelper.context; |
| 942 String code = r''' |
| 943 class A { |
| 944 int field; |
| 945 } |
| 946 main() { |
| 947 int localVar = 42; |
| 948 } |
| 949 '''; |
| 950 Source libSource = contextHelper.addSource("/my_lib.dart", code); |
| 951 // prepare library/unit elements |
| 952 LibraryElement libraryElement = context.computeLibraryElement(libSource); |
| 953 CompilationUnitElement unitElement = libraryElement.definingCompilationUnit; |
| 954 // A |
| 955 ClassElement elementA; |
| 956 { |
| 957 int offset = code.indexOf('A {'); |
| 958 elementA = unitElement.getElementAt(offset); |
| 959 expect(elementA, isNotNull); |
| 960 expect(elementA.enclosingElement, unitElement); |
| 961 expect(elementA.name, 'A'); |
| 962 } |
| 963 // A.field |
| 964 { |
| 965 int offset = code.indexOf('field;'); |
| 966 FieldElement element = unitElement.getElementAt(offset); |
| 967 expect(element, isNotNull); |
| 968 expect(element.enclosingElement, elementA); |
| 969 expect(element.name, 'field'); |
| 970 } |
| 971 // main |
| 972 FunctionElement mainElement; |
| 973 { |
| 974 int offset = code.indexOf('main() {'); |
| 975 mainElement = unitElement.getElementAt(offset); |
| 976 expect(mainElement, isNotNull); |
| 977 expect(mainElement.enclosingElement, unitElement); |
| 978 expect(mainElement.name, 'main'); |
| 979 } |
| 980 // main.localVar |
| 981 { |
| 982 int offset = code.indexOf('localVar'); |
| 983 LocalVariableElement element = unitElement.getElementAt(offset); |
| 984 expect(element, isNotNull); |
| 985 expect(element.enclosingElement, mainElement); |
| 986 expect(element.name, 'localVar'); |
| 987 } |
| 988 // null |
| 989 expect(unitElement.getElementAt(1000), isNull); |
| 990 } |
| 991 |
| 992 void test_getElementAt_multipleUnitsInLibrary() { |
| 993 AnalysisContextHelper contextHelper = new AnalysisContextHelper(); |
| 994 AnalysisContext context = contextHelper.context; |
| 995 Source libSource = contextHelper.addSource( |
| 996 "/my_lib.dart", |
| 997 r''' |
| 998 library my_lib; |
| 999 part 'unit_a.dart'; |
| 1000 part 'unit_b.dart'; |
| 1001 '''); |
| 1002 Source unitSourceA = |
| 1003 contextHelper.addSource("/unit_a.dart", 'part of my_lib;class A {}'); |
| 1004 Source unitSourceB = |
| 1005 contextHelper.addSource("/unit_b.dart", 'part of my_lib;class B {}'); |
| 1006 int offset = 'part of my_lib;class A {}'.indexOf('A {}'); |
| 1007 // prepare library/unit elements |
| 1008 context.computeLibraryElement(libSource); |
| 1009 CompilationUnitElement unitElementA = |
| 1010 context.getCompilationUnitElement(unitSourceA, libSource); |
| 1011 CompilationUnitElement unitElementB = |
| 1012 context.getCompilationUnitElement(unitSourceB, libSource); |
| 1013 // A |
| 1014 { |
| 1015 ClassElement element = unitElementA.getElementAt(offset); |
| 1016 expect(element, isNotNull); |
| 1017 expect(element.enclosingElement, unitElementA); |
| 1018 expect(element.name, 'A'); |
| 1019 } |
| 1020 // B |
| 1021 { |
| 1022 ClassElement element = unitElementB.getElementAt(offset); |
| 1023 expect(element, isNotNull); |
| 1024 expect(element.enclosingElement, unitElementB); |
| 1025 expect(element.name, 'B'); |
| 1026 } |
| 1027 } |
| 1028 |
| 1029 void test_getEnum_declared() { |
| 1030 TestTypeProvider typeProvider = new TestTypeProvider(); |
| 1031 CompilationUnitElementImpl unit = |
| 1032 ElementFactory.compilationUnit("/lib.dart"); |
| 1033 String enumName = "E"; |
| 1034 ClassElement enumElement = |
| 1035 ElementFactory.enumElement(typeProvider, enumName); |
| 1036 unit.enums = <ClassElement>[enumElement]; |
| 1037 expect(unit.getEnum(enumName), same(enumElement)); |
| 1038 } |
| 1039 |
| 1040 void test_getEnum_undeclared() { |
| 1041 TestTypeProvider typeProvider = new TestTypeProvider(); |
| 1042 CompilationUnitElementImpl unit = |
| 1043 ElementFactory.compilationUnit("/lib.dart"); |
| 1044 String enumName = "E"; |
| 1045 ClassElement enumElement = |
| 1046 ElementFactory.enumElement(typeProvider, enumName); |
| 1047 unit.enums = <ClassElement>[enumElement]; |
| 1048 expect(unit.getEnum("${enumName}x"), isNull); |
| 1049 } |
| 1050 |
| 1051 void test_getType_declared() { |
| 1052 CompilationUnitElementImpl unit = |
| 1053 ElementFactory.compilationUnit("/lib.dart"); |
| 1054 String className = "C"; |
| 1055 ClassElement classElement = ElementFactory.classElement2(className); |
| 1056 unit.types = <ClassElement>[classElement]; |
| 1057 expect(unit.getType(className), same(classElement)); |
| 1058 } |
| 1059 |
| 1060 void test_getType_undeclared() { |
| 1061 CompilationUnitElementImpl unit = |
| 1062 ElementFactory.compilationUnit("/lib.dart"); |
| 1063 String className = "C"; |
| 1064 ClassElement classElement = ElementFactory.classElement2(className); |
| 1065 unit.types = <ClassElement>[classElement]; |
| 1066 expect(unit.getType("${className}x"), isNull); |
| 1067 } |
| 1068 } |
| 1069 |
| 1070 @reflectiveTest |
| 1071 class ElementImplTest extends EngineTestCase { |
| 1072 void test_equals() { |
| 1073 LibraryElementImpl library = |
| 1074 ElementFactory.library(createAnalysisContext(), "lib"); |
| 1075 ClassElementImpl classElement = ElementFactory.classElement2("C"); |
| 1076 (library.definingCompilationUnit as CompilationUnitElementImpl).types = |
| 1077 <ClassElement>[classElement]; |
| 1078 FieldElement field = ElementFactory.fieldElement( |
| 1079 "next", false, false, false, classElement.type); |
| 1080 classElement.fields = <FieldElement>[field]; |
| 1081 expect(field == field, isTrue); |
| 1082 expect(field == field.getter, isFalse); |
| 1083 expect(field == field.setter, isFalse); |
| 1084 expect(field.getter == field.setter, isFalse); |
| 1085 } |
| 1086 |
| 1087 void test_isAccessibleIn_private_differentLibrary() { |
| 1088 AnalysisContext context = createAnalysisContext(); |
| 1089 LibraryElementImpl library1 = ElementFactory.library(context, "lib1"); |
| 1090 ClassElement classElement = ElementFactory.classElement2("_C"); |
| 1091 (library1.definingCompilationUnit as CompilationUnitElementImpl).types = |
| 1092 <ClassElement>[classElement]; |
| 1093 LibraryElementImpl library2 = ElementFactory.library(context, "lib2"); |
| 1094 expect(classElement.isAccessibleIn(library2), isFalse); |
| 1095 } |
| 1096 |
| 1097 void test_isAccessibleIn_private_sameLibrary() { |
| 1098 LibraryElementImpl library = |
| 1099 ElementFactory.library(createAnalysisContext(), "lib"); |
| 1100 ClassElement classElement = ElementFactory.classElement2("_C"); |
| 1101 (library.definingCompilationUnit as CompilationUnitElementImpl).types = |
| 1102 <ClassElement>[classElement]; |
| 1103 expect(classElement.isAccessibleIn(library), isTrue); |
| 1104 } |
| 1105 |
| 1106 void test_isAccessibleIn_public_differentLibrary() { |
| 1107 AnalysisContext context = createAnalysisContext(); |
| 1108 LibraryElementImpl library1 = ElementFactory.library(context, "lib1"); |
| 1109 ClassElement classElement = ElementFactory.classElement2("C"); |
| 1110 (library1.definingCompilationUnit as CompilationUnitElementImpl).types = |
| 1111 <ClassElement>[classElement]; |
| 1112 LibraryElementImpl library2 = ElementFactory.library(context, "lib2"); |
| 1113 expect(classElement.isAccessibleIn(library2), isTrue); |
| 1114 } |
| 1115 |
| 1116 void test_isAccessibleIn_public_sameLibrary() { |
| 1117 LibraryElementImpl library = |
| 1118 ElementFactory.library(createAnalysisContext(), "lib"); |
| 1119 ClassElement classElement = ElementFactory.classElement2("C"); |
| 1120 (library.definingCompilationUnit as CompilationUnitElementImpl).types = |
| 1121 <ClassElement>[classElement]; |
| 1122 expect(classElement.isAccessibleIn(library), isTrue); |
| 1123 } |
| 1124 |
| 1125 void test_isPrivate_false() { |
| 1126 Element element = ElementFactory.classElement2("C"); |
| 1127 expect(element.isPrivate, isFalse); |
| 1128 } |
| 1129 |
| 1130 void test_isPrivate_null() { |
| 1131 Element element = ElementFactory.classElement2(null); |
| 1132 expect(element.isPrivate, isTrue); |
| 1133 } |
| 1134 |
| 1135 void test_isPrivate_true() { |
| 1136 Element element = ElementFactory.classElement2("_C"); |
| 1137 expect(element.isPrivate, isTrue); |
| 1138 } |
| 1139 |
| 1140 void test_isPublic_false() { |
| 1141 Element element = ElementFactory.classElement2("_C"); |
| 1142 expect(element.isPublic, isFalse); |
| 1143 } |
| 1144 |
| 1145 void test_isPublic_null() { |
| 1146 Element element = ElementFactory.classElement2(null); |
| 1147 expect(element.isPublic, isFalse); |
| 1148 } |
| 1149 |
| 1150 void test_isPublic_true() { |
| 1151 Element element = ElementFactory.classElement2("C"); |
| 1152 expect(element.isPublic, isTrue); |
| 1153 } |
| 1154 |
| 1155 void test_SORT_BY_OFFSET() { |
| 1156 ClassElementImpl classElementA = ElementFactory.classElement2("A"); |
| 1157 classElementA.nameOffset = 1; |
| 1158 ClassElementImpl classElementB = ElementFactory.classElement2("B"); |
| 1159 classElementB.nameOffset = 2; |
| 1160 expect(Element.SORT_BY_OFFSET(classElementA, classElementA), 0); |
| 1161 expect(Element.SORT_BY_OFFSET(classElementA, classElementB) < 0, isTrue); |
| 1162 expect(Element.SORT_BY_OFFSET(classElementB, classElementA) > 0, isTrue); |
| 1163 } |
| 1164 } |
| 1165 |
| 1166 @reflectiveTest |
| 1167 class ElementKindTest extends EngineTestCase { |
| 1168 void test_of_nonNull() { |
| 1169 expect(ElementKind.of(ElementFactory.classElement2("A")), |
| 1170 same(ElementKind.CLASS)); |
| 1171 } |
| 1172 |
| 1173 void test_of_null() { |
| 1174 expect(ElementKind.of(null), same(ElementKind.ERROR)); |
| 1175 } |
| 1176 } |
| 1177 |
| 1178 @reflectiveTest |
| 1179 class ElementLocationImplTest extends EngineTestCase { |
| 1180 void test_create_encoding() { |
| 1181 String encoding = "a;b;c"; |
| 1182 ElementLocationImpl location = new ElementLocationImpl.con2(encoding); |
| 1183 expect(location.encoding, encoding); |
| 1184 } |
| 1185 |
| 1186 /** |
| 1187 * For example unnamed constructor. |
| 1188 */ |
| 1189 void test_create_encoding_emptyLast() { |
| 1190 String encoding = "a;b;c;"; |
| 1191 ElementLocationImpl location = new ElementLocationImpl.con2(encoding); |
| 1192 expect(location.encoding, encoding); |
| 1193 } |
| 1194 |
| 1195 void test_equals_equal() { |
| 1196 String encoding = "a;b;c"; |
| 1197 ElementLocationImpl first = new ElementLocationImpl.con2(encoding); |
| 1198 ElementLocationImpl second = new ElementLocationImpl.con2(encoding); |
| 1199 expect(first == second, isTrue); |
| 1200 } |
| 1201 |
| 1202 void test_equals_notEqual_differentLengths() { |
| 1203 ElementLocationImpl first = new ElementLocationImpl.con2("a;b;c"); |
| 1204 ElementLocationImpl second = new ElementLocationImpl.con2("a;b;c;d"); |
| 1205 expect(first == second, isFalse); |
| 1206 } |
| 1207 |
| 1208 void test_equals_notEqual_notLocation() { |
| 1209 ElementLocationImpl first = new ElementLocationImpl.con2("a;b;c"); |
| 1210 expect(first == "a;b;d", isFalse); |
| 1211 } |
| 1212 |
| 1213 void test_equals_notEqual_sameLengths() { |
| 1214 ElementLocationImpl first = new ElementLocationImpl.con2("a;b;c"); |
| 1215 ElementLocationImpl second = new ElementLocationImpl.con2("a;b;d"); |
| 1216 expect(first == second, isFalse); |
| 1217 } |
| 1218 |
| 1219 void test_getComponents() { |
| 1220 String encoding = "a;b;c"; |
| 1221 ElementLocationImpl location = new ElementLocationImpl.con2(encoding); |
| 1222 List<String> components = location.components; |
| 1223 expect(components, hasLength(3)); |
| 1224 expect(components[0], "a"); |
| 1225 expect(components[1], "b"); |
| 1226 expect(components[2], "c"); |
| 1227 } |
| 1228 |
| 1229 void test_getEncoding() { |
| 1230 String encoding = "a;b;c;;d"; |
| 1231 ElementLocationImpl location = new ElementLocationImpl.con2(encoding); |
| 1232 expect(location.encoding, encoding); |
| 1233 } |
| 1234 |
| 1235 void test_hashCode_equal() { |
| 1236 String encoding = "a;b;c"; |
| 1237 ElementLocationImpl first = new ElementLocationImpl.con2(encoding); |
| 1238 ElementLocationImpl second = new ElementLocationImpl.con2(encoding); |
| 1239 expect(first.hashCode == second.hashCode, isTrue); |
| 1240 } |
| 1241 } |
| 1242 |
| 1243 @reflectiveTest |
| 1244 class FieldElementImplTest extends EngineTestCase { |
| 1245 void test_computeNode() { |
| 1246 AnalysisContextHelper contextHelper = new AnalysisContextHelper(); |
| 1247 AnalysisContext context = contextHelper.context; |
| 1248 Source source = contextHelper.addSource( |
| 1249 "/test.dart", |
| 1250 r''' |
| 1251 class A { |
| 1252 int a; |
| 1253 } |
| 1254 enum B {B1, B2, B3}'''); |
| 1255 // prepare CompilationUnitElement |
| 1256 LibraryElement libraryElement = context.computeLibraryElement(source); |
| 1257 CompilationUnitElement unitElement = libraryElement.definingCompilationUnit; |
| 1258 // A |
| 1259 { |
| 1260 FieldElement elementA = unitElement.getType("A").getField('a'); |
| 1261 VariableDeclaration nodeA = elementA.computeNode(); |
| 1262 expect(nodeA, isNotNull); |
| 1263 expect(nodeA.name.name, "a"); |
| 1264 expect(nodeA.element, same(elementA)); |
| 1265 } |
| 1266 // B |
| 1267 { |
| 1268 FieldElement elementB = unitElement.getEnum("B").getField('B2'); |
| 1269 EnumConstantDeclaration nodeB = elementB.computeNode(); |
| 1270 expect(nodeB, isNotNull); |
| 1271 expect(nodeB.name.name, "B2"); |
| 1272 expect(nodeB.element, same(elementB)); |
| 1273 } |
| 1274 } |
| 1275 } |
| 1276 |
| 1277 @reflectiveTest |
| 1278 class FunctionTypeImplTest extends EngineTestCase { |
| 1279 void test_creation() { |
| 1280 expect( |
| 1281 new FunctionTypeImpl( |
| 1282 new FunctionElementImpl.forNode(AstFactory.identifier3("f"))), |
| 1283 isNotNull); |
| 1284 } |
| 1285 |
| 1286 void test_equality_recursive() { |
| 1287 FunctionTypeAliasElementImpl s = |
| 1288 ElementFactory.functionTypeAliasElement('s'); |
| 1289 FunctionTypeAliasElementImpl t = |
| 1290 ElementFactory.functionTypeAliasElement('t'); |
| 1291 FunctionTypeAliasElementImpl u = |
| 1292 ElementFactory.functionTypeAliasElement('u'); |
| 1293 FunctionTypeAliasElementImpl v = |
| 1294 ElementFactory.functionTypeAliasElement('v'); |
| 1295 s.returnType = t.type; |
| 1296 t.returnType = s.type; |
| 1297 u.returnType = v.type; |
| 1298 v.returnType = u.type; |
| 1299 // We don't care whether the types compare equal or not. We just need the |
| 1300 // computation to terminate. |
| 1301 expect(s.type == u.type, new isInstanceOf<bool>()); |
| 1302 } |
| 1303 |
| 1304 void test_getElement() { |
| 1305 FunctionElementImpl typeElement = |
| 1306 new FunctionElementImpl.forNode(AstFactory.identifier3("f")); |
| 1307 FunctionTypeImpl type = new FunctionTypeImpl(typeElement); |
| 1308 expect(type.element, typeElement); |
| 1309 } |
| 1310 |
| 1311 void test_getNamedParameterTypes() { |
| 1312 FunctionTypeImpl type = new FunctionTypeImpl( |
| 1313 new FunctionElementImpl.forNode(AstFactory.identifier3("f"))); |
| 1314 Map<String, DartType> types = type.namedParameterTypes; |
| 1315 expect(types, hasLength(0)); |
| 1316 } |
| 1317 |
| 1318 void test_getNormalParameterTypes() { |
| 1319 FunctionTypeImpl type = new FunctionTypeImpl( |
| 1320 new FunctionElementImpl.forNode(AstFactory.identifier3("f"))); |
| 1321 List<DartType> types = type.normalParameterTypes; |
| 1322 expect(types, hasLength(0)); |
| 1323 } |
| 1324 |
| 1325 void test_getReturnType() { |
| 1326 DartType expectedReturnType = VoidTypeImpl.instance; |
| 1327 FunctionElementImpl functionElement = |
| 1328 new FunctionElementImpl.forNode(AstFactory.identifier3("f")); |
| 1329 functionElement.returnType = expectedReturnType; |
| 1330 FunctionTypeImpl type = new FunctionTypeImpl(functionElement); |
| 1331 DartType returnType = type.returnType; |
| 1332 expect(returnType, expectedReturnType); |
| 1333 } |
| 1334 |
| 1335 void test_getTypeArguments() { |
| 1336 FunctionTypeImpl type = new FunctionTypeImpl( |
| 1337 new FunctionElementImpl.forNode(AstFactory.identifier3("f"))); |
| 1338 List<DartType> types = type.typeArguments; |
| 1339 expect(types, hasLength(0)); |
| 1340 } |
| 1341 |
| 1342 void test_hashCode_element() { |
| 1343 FunctionTypeImpl type = new FunctionTypeImpl( |
| 1344 new FunctionElementImpl.forNode(AstFactory.identifier3("f"))); |
| 1345 type.hashCode; |
| 1346 } |
| 1347 |
| 1348 void test_hashCode_noElement() { |
| 1349 FunctionTypeImpl type = new FunctionTypeImpl(null); |
| 1350 type.hashCode; |
| 1351 } |
| 1352 |
| 1353 void test_hashCode_recursive() { |
| 1354 FunctionTypeAliasElementImpl s = |
| 1355 ElementFactory.functionTypeAliasElement('s'); |
| 1356 FunctionTypeAliasElementImpl t = |
| 1357 ElementFactory.functionTypeAliasElement('t'); |
| 1358 s.returnType = t.type; |
| 1359 t.returnType = s.type; |
| 1360 // We don't care what the hash code is. We just need its computation to |
| 1361 // terminate. |
| 1362 expect(t.type.hashCode, new isInstanceOf<int>()); |
| 1363 } |
| 1364 |
| 1365 void test_isAssignableTo_normalAndPositionalArgs() { |
| 1366 // ([a]) -> void <: (a) -> void |
| 1367 ClassElement a = ElementFactory.classElement2("A"); |
| 1368 FunctionType t = |
| 1369 ElementFactory.functionElement6("t", null, <ClassElement>[a]).type; |
| 1370 FunctionType s = |
| 1371 ElementFactory.functionElement5("s", <ClassElement>[a]).type; |
| 1372 expect(t.isSubtypeOf(s), isTrue); |
| 1373 expect(s.isSubtypeOf(t), isFalse); |
| 1374 // assignable iff subtype |
| 1375 expect(t.isAssignableTo(s), isTrue); |
| 1376 expect(s.isAssignableTo(t), isFalse); |
| 1377 } |
| 1378 |
| 1379 void test_isSubtypeOf_baseCase_classFunction() { |
| 1380 // () -> void <: Function |
| 1381 ClassElementImpl functionElement = ElementFactory.classElement2("Function"); |
| 1382 InterfaceTypeImpl functionType = |
| 1383 new _FunctionTypeImplTest_isSubtypeOf_baseCase_classFunction( |
| 1384 functionElement); |
| 1385 FunctionType f = ElementFactory.functionElement("f").type; |
| 1386 expect(f.isSubtypeOf(functionType), isTrue); |
| 1387 } |
| 1388 |
| 1389 void test_isSubtypeOf_baseCase_notFunctionType() { |
| 1390 // class C |
| 1391 // ! () -> void <: C |
| 1392 FunctionType f = ElementFactory.functionElement("f").type; |
| 1393 InterfaceType t = ElementFactory.classElement2("C").type; |
| 1394 expect(f.isSubtypeOf(t), isFalse); |
| 1395 } |
| 1396 |
| 1397 void test_isSubtypeOf_baseCase_null() { |
| 1398 // ! () -> void <: null |
| 1399 FunctionType f = ElementFactory.functionElement("f").type; |
| 1400 expect(f.isSubtypeOf(null), isFalse); |
| 1401 } |
| 1402 |
| 1403 void test_isSubtypeOf_baseCase_self() { |
| 1404 // () -> void <: () -> void |
| 1405 FunctionType f = ElementFactory.functionElement("f").type; |
| 1406 expect(f.isSubtypeOf(f), isTrue); |
| 1407 } |
| 1408 |
| 1409 void test_isSubtypeOf_namedParameters_isAssignable() { |
| 1410 // B extends A |
| 1411 // ({name: A}) -> void <: ({name: B}) -> void |
| 1412 // ({name: B}) -> void <: ({name: A}) -> void |
| 1413 ClassElement a = ElementFactory.classElement2("A"); |
| 1414 ClassElement b = ElementFactory.classElement("B", a.type); |
| 1415 FunctionType t = ElementFactory.functionElement4( |
| 1416 "t", null, null, <String>["name"], <ClassElement>[a]).type; |
| 1417 FunctionType s = ElementFactory.functionElement4( |
| 1418 "s", null, null, <String>["name"], <ClassElement>[b]).type; |
| 1419 expect(t.isSubtypeOf(s), isTrue); |
| 1420 expect(s.isSubtypeOf(t), isTrue); |
| 1421 } |
| 1422 |
| 1423 void test_isSubtypeOf_namedParameters_isNotAssignable() { |
| 1424 // ! ({name: A}) -> void <: ({name: B}) -> void |
| 1425 FunctionType t = ElementFactory.functionElement4( |
| 1426 "t", |
| 1427 null, |
| 1428 null, |
| 1429 <String>["name"], |
| 1430 <ClassElement>[ElementFactory.classElement2("A")]).type; |
| 1431 FunctionType s = ElementFactory.functionElement4( |
| 1432 "s", |
| 1433 null, |
| 1434 null, |
| 1435 <String>["name"], |
| 1436 <ClassElement>[ElementFactory.classElement2("B")]).type; |
| 1437 expect(t.isSubtypeOf(s), isFalse); |
| 1438 } |
| 1439 |
| 1440 void test_isSubtypeOf_namedParameters_namesDifferent() { |
| 1441 // B extends A |
| 1442 // void t({A name}) {} |
| 1443 // void s({A diff}) {} |
| 1444 // ! t <: s |
| 1445 // ! s <: t |
| 1446 ClassElement a = ElementFactory.classElement2("A"); |
| 1447 ClassElement b = ElementFactory.classElement("B", a.type); |
| 1448 FunctionType t = ElementFactory.functionElement4( |
| 1449 "t", null, null, <String>["name"], <ClassElement>[a]).type; |
| 1450 FunctionType s = ElementFactory.functionElement4( |
| 1451 "s", null, null, <String>["diff"], <ClassElement>[b]).type; |
| 1452 expect(t.isSubtypeOf(s), isFalse); |
| 1453 expect(s.isSubtypeOf(t), isFalse); |
| 1454 } |
| 1455 |
| 1456 void test_isSubtypeOf_namedParameters_orderOfParams() { |
| 1457 // B extends A |
| 1458 // ({A: A, B: B}) -> void <: ({B: B, A: A}) -> void |
| 1459 ClassElement a = ElementFactory.classElement2("A"); |
| 1460 ClassElement b = ElementFactory.classElement("B", a.type); |
| 1461 FunctionType t = ElementFactory.functionElement4( |
| 1462 "t", null, null, <String>["A", "B"], <ClassElement>[a, b]).type; |
| 1463 FunctionType s = ElementFactory.functionElement4( |
| 1464 "s", null, null, <String>["B", "A"], <ClassElement>[b, a]).type; |
| 1465 expect(t.isSubtypeOf(s), isTrue); |
| 1466 } |
| 1467 |
| 1468 void test_isSubtypeOf_namedParameters_orderOfParams2() { |
| 1469 // B extends A |
| 1470 // ! ({B: B}) -> void <: ({B: B, A: A}) -> void |
| 1471 ClassElement a = ElementFactory.classElement2("A"); |
| 1472 ClassElement b = ElementFactory.classElement("B", a.type); |
| 1473 FunctionType t = ElementFactory.functionElement4( |
| 1474 "t", null, null, <String>["B"], <ClassElement>[b]).type; |
| 1475 FunctionType s = ElementFactory.functionElement4( |
| 1476 "s", null, null, <String>["B", "A"], <ClassElement>[b, a]).type; |
| 1477 expect(t.isSubtypeOf(s), isFalse); |
| 1478 } |
| 1479 |
| 1480 void test_isSubtypeOf_namedParameters_orderOfParams3() { |
| 1481 // B extends A |
| 1482 // ({A: A, B: B}) -> void <: ({A: A}) -> void |
| 1483 ClassElement a = ElementFactory.classElement2("A"); |
| 1484 ClassElement b = ElementFactory.classElement("B", a.type); |
| 1485 FunctionType t = ElementFactory.functionElement4( |
| 1486 "t", null, null, <String>["A", "B"], <ClassElement>[a, b]).type; |
| 1487 FunctionType s = ElementFactory.functionElement4( |
| 1488 "s", null, null, <String>["B"], <ClassElement>[b]).type; |
| 1489 expect(t.isSubtypeOf(s), isTrue); |
| 1490 } |
| 1491 |
| 1492 void test_isSubtypeOf_namedParameters_sHasMoreParams() { |
| 1493 // B extends A |
| 1494 // ! ({name: A}) -> void <: ({name: B, name2: B}) -> void |
| 1495 ClassElement a = ElementFactory.classElement2("A"); |
| 1496 ClassElement b = ElementFactory.classElement("B", a.type); |
| 1497 FunctionType t = ElementFactory.functionElement4( |
| 1498 "t", null, null, <String>["name"], <ClassElement>[a]).type; |
| 1499 FunctionType s = ElementFactory.functionElement4( |
| 1500 "s", null, null, <String>["name", "name2"], <ClassElement>[b, b]).type; |
| 1501 expect(t.isSubtypeOf(s), isFalse); |
| 1502 } |
| 1503 |
| 1504 void test_isSubtypeOf_namedParameters_tHasMoreParams() { |
| 1505 // B extends A |
| 1506 // ({name: A, name2: A}) -> void <: ({name: B}) -> void |
| 1507 ClassElement a = ElementFactory.classElement2("A"); |
| 1508 ClassElement b = ElementFactory.classElement("B", a.type); |
| 1509 FunctionType t = ElementFactory.functionElement4( |
| 1510 "t", null, null, <String>["name", "name2"], <ClassElement>[a, a]).type; |
| 1511 FunctionType s = ElementFactory.functionElement4( |
| 1512 "s", null, null, <String>["name"], <ClassElement>[b]).type; |
| 1513 expect(t.isSubtypeOf(s), isTrue); |
| 1514 } |
| 1515 |
| 1516 void test_isSubtypeOf_normalAndPositionalArgs_1() { |
| 1517 // ([a]) -> void <: (a) -> void |
| 1518 ClassElement a = ElementFactory.classElement2("A"); |
| 1519 FunctionType t = |
| 1520 ElementFactory.functionElement6("t", null, <ClassElement>[a]).type; |
| 1521 FunctionType s = |
| 1522 ElementFactory.functionElement5("s", <ClassElement>[a]).type; |
| 1523 expect(t.isSubtypeOf(s), isTrue); |
| 1524 expect(s.isSubtypeOf(t), isFalse); |
| 1525 } |
| 1526 |
| 1527 void test_isSubtypeOf_normalAndPositionalArgs_2() { |
| 1528 // (a, [a]) -> void <: (a) -> void |
| 1529 ClassElement a = ElementFactory.classElement2("A"); |
| 1530 FunctionType t = ElementFactory |
| 1531 .functionElement6("t", <ClassElement>[a], <ClassElement>[a]).type; |
| 1532 FunctionType s = |
| 1533 ElementFactory.functionElement5("s", <ClassElement>[a]).type; |
| 1534 expect(t.isSubtypeOf(s), isTrue); |
| 1535 expect(s.isSubtypeOf(t), isFalse); |
| 1536 } |
| 1537 |
| 1538 void test_isSubtypeOf_normalAndPositionalArgs_3() { |
| 1539 // ([a]) -> void <: () -> void |
| 1540 ClassElement a = ElementFactory.classElement2("A"); |
| 1541 FunctionType t = |
| 1542 ElementFactory.functionElement6("t", null, <ClassElement>[a]).type; |
| 1543 FunctionType s = ElementFactory.functionElement("s").type; |
| 1544 expect(t.isSubtypeOf(s), isTrue); |
| 1545 expect(s.isSubtypeOf(t), isFalse); |
| 1546 } |
| 1547 |
| 1548 void test_isSubtypeOf_normalAndPositionalArgs_4() { |
| 1549 // (a, b, [c, d, e]) -> void <: (a, b, c, [d]) -> void |
| 1550 ClassElement a = ElementFactory.classElement2("A"); |
| 1551 ClassElement b = ElementFactory.classElement2("B"); |
| 1552 ClassElement c = ElementFactory.classElement2("C"); |
| 1553 ClassElement d = ElementFactory.classElement2("D"); |
| 1554 ClassElement e = ElementFactory.classElement2("E"); |
| 1555 FunctionType t = ElementFactory.functionElement6( |
| 1556 "t", <ClassElement>[a, b], <ClassElement>[c, d, e]).type; |
| 1557 FunctionType s = ElementFactory |
| 1558 .functionElement6("s", <ClassElement>[a, b, c], <ClassElement>[d]).type; |
| 1559 expect(t.isSubtypeOf(s), isTrue); |
| 1560 expect(s.isSubtypeOf(t), isFalse); |
| 1561 } |
| 1562 |
| 1563 void test_isSubtypeOf_normalParameters_isAssignable() { |
| 1564 // B extends A |
| 1565 // (a) -> void <: (b) -> void |
| 1566 // (b) -> void <: (a) -> void |
| 1567 ClassElement a = ElementFactory.classElement2("A"); |
| 1568 ClassElement b = ElementFactory.classElement("B", a.type); |
| 1569 FunctionType t = |
| 1570 ElementFactory.functionElement5("t", <ClassElement>[a]).type; |
| 1571 FunctionType s = |
| 1572 ElementFactory.functionElement5("s", <ClassElement>[b]).type; |
| 1573 expect(t.isSubtypeOf(s), isTrue); |
| 1574 expect(s.isSubtypeOf(t), isTrue); |
| 1575 } |
| 1576 |
| 1577 void test_isSubtypeOf_normalParameters_isNotAssignable() { |
| 1578 // ! (a) -> void <: (b) -> void |
| 1579 FunctionType t = ElementFactory.functionElement5( |
| 1580 "t", <ClassElement>[ElementFactory.classElement2("A")]).type; |
| 1581 FunctionType s = ElementFactory.functionElement5( |
| 1582 "s", <ClassElement>[ElementFactory.classElement2("B")]).type; |
| 1583 expect(t.isSubtypeOf(s), isFalse); |
| 1584 } |
| 1585 |
| 1586 void test_isSubtypeOf_normalParameters_sHasMoreParams() { |
| 1587 // B extends A |
| 1588 // ! (a) -> void <: (b, b) -> void |
| 1589 ClassElement a = ElementFactory.classElement2("A"); |
| 1590 ClassElement b = ElementFactory.classElement("B", a.type); |
| 1591 FunctionType t = |
| 1592 ElementFactory.functionElement5("t", <ClassElement>[a]).type; |
| 1593 FunctionType s = |
| 1594 ElementFactory.functionElement5("s", <ClassElement>[b, b]).type; |
| 1595 expect(t.isSubtypeOf(s), isFalse); |
| 1596 } |
| 1597 |
| 1598 void test_isSubtypeOf_normalParameters_tHasMoreParams() { |
| 1599 // B extends A |
| 1600 // ! (a, a) -> void <: (a) -> void |
| 1601 ClassElement a = ElementFactory.classElement2("A"); |
| 1602 ClassElement b = ElementFactory.classElement("B", a.type); |
| 1603 FunctionType t = |
| 1604 ElementFactory.functionElement5("t", <ClassElement>[a, a]).type; |
| 1605 FunctionType s = |
| 1606 ElementFactory.functionElement5("s", <ClassElement>[b]).type; |
| 1607 // note, this is a different assertion from the other "tHasMoreParams" |
| 1608 // tests, this is intentional as it is a difference of the "normal |
| 1609 // parameters" |
| 1610 expect(t.isSubtypeOf(s), isFalse); |
| 1611 } |
| 1612 |
| 1613 void test_isSubtypeOf_Object() { |
| 1614 // () -> void <: Object |
| 1615 FunctionType f = ElementFactory.functionElement("f").type; |
| 1616 InterfaceType t = ElementFactory.object.type; |
| 1617 expect(f.isSubtypeOf(t), isTrue); |
| 1618 } |
| 1619 |
| 1620 void test_isSubtypeOf_positionalParameters_isAssignable() { |
| 1621 // B extends A |
| 1622 // ([a]) -> void <: ([b]) -> void |
| 1623 // ([b]) -> void <: ([a]) -> void |
| 1624 ClassElement a = ElementFactory.classElement2("A"); |
| 1625 ClassElement b = ElementFactory.classElement("B", a.type); |
| 1626 FunctionType t = |
| 1627 ElementFactory.functionElement6("t", null, <ClassElement>[a]).type; |
| 1628 FunctionType s = |
| 1629 ElementFactory.functionElement6("s", null, <ClassElement>[b]).type; |
| 1630 expect(t.isSubtypeOf(s), isTrue); |
| 1631 expect(s.isSubtypeOf(t), isTrue); |
| 1632 } |
| 1633 |
| 1634 void test_isSubtypeOf_positionalParameters_isNotAssignable() { |
| 1635 // ! ([a]) -> void <: ([b]) -> void |
| 1636 FunctionType t = ElementFactory.functionElement6( |
| 1637 "t", null, <ClassElement>[ElementFactory.classElement2("A")]).type; |
| 1638 FunctionType s = ElementFactory.functionElement6( |
| 1639 "s", null, <ClassElement>[ElementFactory.classElement2("B")]).type; |
| 1640 expect(t.isSubtypeOf(s), isFalse); |
| 1641 } |
| 1642 |
| 1643 void test_isSubtypeOf_positionalParameters_sHasMoreParams() { |
| 1644 // B extends A |
| 1645 // ! ([a]) -> void <: ([b, b]) -> void |
| 1646 ClassElement a = ElementFactory.classElement2("A"); |
| 1647 ClassElement b = ElementFactory.classElement("B", a.type); |
| 1648 FunctionType t = |
| 1649 ElementFactory.functionElement6("t", null, <ClassElement>[a]).type; |
| 1650 FunctionType s = |
| 1651 ElementFactory.functionElement6("s", null, <ClassElement>[b, b]).type; |
| 1652 expect(t.isSubtypeOf(s), isFalse); |
| 1653 } |
| 1654 |
| 1655 void test_isSubtypeOf_positionalParameters_tHasMoreParams() { |
| 1656 // B extends A |
| 1657 // ([a, a]) -> void <: ([b]) -> void |
| 1658 ClassElement a = ElementFactory.classElement2("A"); |
| 1659 ClassElement b = ElementFactory.classElement("B", a.type); |
| 1660 FunctionType t = |
| 1661 ElementFactory.functionElement6("t", null, <ClassElement>[a, a]).type; |
| 1662 FunctionType s = |
| 1663 ElementFactory.functionElement6("s", null, <ClassElement>[b]).type; |
| 1664 expect(t.isSubtypeOf(s), isTrue); |
| 1665 } |
| 1666 |
| 1667 void test_isSubtypeOf_returnType_sIsVoid() { |
| 1668 // () -> void <: void |
| 1669 FunctionType t = ElementFactory.functionElement("t").type; |
| 1670 FunctionType s = ElementFactory.functionElement("s").type; |
| 1671 // function s has the implicit return type of void, we assert it here |
| 1672 expect(VoidTypeImpl.instance == s.returnType, isTrue); |
| 1673 expect(t.isSubtypeOf(s), isTrue); |
| 1674 } |
| 1675 |
| 1676 void test_isSubtypeOf_returnType_tAssignableToS() { |
| 1677 // B extends A |
| 1678 // () -> A <: () -> B |
| 1679 // () -> B <: () -> A |
| 1680 ClassElement a = ElementFactory.classElement2("A"); |
| 1681 ClassElement b = ElementFactory.classElement("B", a.type); |
| 1682 FunctionType t = ElementFactory.functionElement2("t", a).type; |
| 1683 FunctionType s = ElementFactory.functionElement2("s", b).type; |
| 1684 expect(t.isSubtypeOf(s), isTrue); |
| 1685 expect(s.isSubtypeOf(t), isTrue); |
| 1686 } |
| 1687 |
| 1688 void test_isSubtypeOf_returnType_tNotAssignableToS() { |
| 1689 // ! () -> A <: () -> B |
| 1690 FunctionType t = ElementFactory |
| 1691 .functionElement2("t", ElementFactory.classElement2("A")) |
| 1692 .type; |
| 1693 FunctionType s = ElementFactory |
| 1694 .functionElement2("s", ElementFactory.classElement2("B")) |
| 1695 .type; |
| 1696 expect(t.isSubtypeOf(s), isFalse); |
| 1697 } |
| 1698 |
| 1699 void test_isSubtypeOf_typeParameters_matchesBounds() { |
| 1700 TestTypeProvider provider = new TestTypeProvider(); |
| 1701 InterfaceType boolType = provider.boolType; |
| 1702 InterfaceType stringType = provider.stringType; |
| 1703 TypeParameterElementImpl parameterB = |
| 1704 new TypeParameterElementImpl.forNode(AstFactory.identifier3("B")); |
| 1705 parameterB.bound = boolType; |
| 1706 TypeParameterTypeImpl typeB = new TypeParameterTypeImpl(parameterB); |
| 1707 TypeParameterElementImpl parameterS = |
| 1708 new TypeParameterElementImpl.forNode(AstFactory.identifier3("S")); |
| 1709 parameterS.bound = stringType; |
| 1710 TypeParameterTypeImpl typeS = new TypeParameterTypeImpl(parameterS); |
| 1711 FunctionElementImpl functionAliasElement = |
| 1712 new FunctionElementImpl.forNode(AstFactory.identifier3("func")); |
| 1713 functionAliasElement.parameters = <ParameterElement>[ |
| 1714 ElementFactory.requiredParameter2("a", typeB), |
| 1715 ElementFactory.positionalParameter2("b", typeS) |
| 1716 ]; |
| 1717 functionAliasElement.returnType = stringType; |
| 1718 FunctionTypeImpl functionAliasType = |
| 1719 new FunctionTypeImpl(functionAliasElement); |
| 1720 functionAliasElement.type = functionAliasType; |
| 1721 FunctionElementImpl functionElement = |
| 1722 new FunctionElementImpl.forNode(AstFactory.identifier3("f")); |
| 1723 functionElement.parameters = <ParameterElement>[ |
| 1724 ElementFactory.requiredParameter2("c", boolType), |
| 1725 ElementFactory.positionalParameter2("d", stringType) |
| 1726 ]; |
| 1727 functionElement.returnType = provider.dynamicType; |
| 1728 FunctionTypeImpl functionType = new FunctionTypeImpl(functionElement); |
| 1729 functionElement.type = functionType; |
| 1730 expect(functionType.isAssignableTo(functionAliasType), isTrue); |
| 1731 } |
| 1732 |
| 1733 void test_isSubtypeOf_wrongFunctionType_normal_named() { |
| 1734 // ! (a) -> void <: ({name: A}) -> void |
| 1735 // ! ({name: A}) -> void <: (a) -> void |
| 1736 ClassElement a = ElementFactory.classElement2("A"); |
| 1737 FunctionType t = |
| 1738 ElementFactory.functionElement5("t", <ClassElement>[a]).type; |
| 1739 FunctionType s = ElementFactory |
| 1740 .functionElement7("s", null, <String>["name"], <ClassElement>[a]).type; |
| 1741 expect(t.isSubtypeOf(s), isFalse); |
| 1742 expect(s.isSubtypeOf(t), isFalse); |
| 1743 } |
| 1744 |
| 1745 void test_isSubtypeOf_wrongFunctionType_optional_named() { |
| 1746 // ! ([a]) -> void <: ({name: A}) -> void |
| 1747 // ! ({name: A}) -> void <: ([a]) -> void |
| 1748 ClassElement a = ElementFactory.classElement2("A"); |
| 1749 FunctionType t = |
| 1750 ElementFactory.functionElement6("t", null, <ClassElement>[a]).type; |
| 1751 FunctionType s = ElementFactory |
| 1752 .functionElement7("s", null, <String>["name"], <ClassElement>[a]).type; |
| 1753 expect(t.isSubtypeOf(s), isFalse); |
| 1754 expect(s.isSubtypeOf(t), isFalse); |
| 1755 } |
| 1756 |
| 1757 void test_namedParameterTypes_pruned_no_type_arguments() { |
| 1758 FunctionTypeAliasElementImpl f = |
| 1759 ElementFactory.functionTypeAliasElement('f'); |
| 1760 FunctionTypeAliasElementImpl g = |
| 1761 ElementFactory.functionTypeAliasElement('g'); |
| 1762 f.parameters = [ElementFactory.namedParameter2('x', g.type)]; |
| 1763 FunctionTypeImpl paramType = f.type.namedParameterTypes['x']; |
| 1764 expect(paramType.prunedTypedefs, hasLength(1)); |
| 1765 expect(paramType.prunedTypedefs[0], same(f)); |
| 1766 } |
| 1767 |
| 1768 void test_namedParameterTypes_pruned_with_type_arguments() { |
| 1769 FunctionTypeAliasElementImpl f = |
| 1770 ElementFactory.functionTypeAliasElement('f'); |
| 1771 FunctionTypeAliasElementImpl g = |
| 1772 ElementFactory.functionTypeAliasElement('g'); |
| 1773 f.typeParameters = [ElementFactory.typeParameterElement('T')]; |
| 1774 f.parameters = [ElementFactory.namedParameter2('x', g.type)]; |
| 1775 FunctionTypeImpl paramType = f.type.namedParameterTypes['x']; |
| 1776 expect(paramType.prunedTypedefs, hasLength(1)); |
| 1777 expect(paramType.prunedTypedefs[0], same(f)); |
| 1778 } |
| 1779 |
| 1780 void test_newPrune_no_previous_prune() { |
| 1781 FunctionTypeAliasElementImpl f = |
| 1782 ElementFactory.functionTypeAliasElement('f'); |
| 1783 FunctionTypeImpl type = f.type; |
| 1784 List<FunctionTypeAliasElement> pruneList = type.newPrune; |
| 1785 expect(pruneList, hasLength(1)); |
| 1786 expect(pruneList[0], same(f)); |
| 1787 } |
| 1788 |
| 1789 void test_newPrune_non_typedef() { |
| 1790 // No pruning needs to be done for function types that aren't associated |
| 1791 // with typedefs because those types can't be directly referred to by the |
| 1792 // user (and hence can't participate in circularities). |
| 1793 FunctionElementImpl f = ElementFactory.functionElement('f'); |
| 1794 FunctionTypeImpl type = f.type; |
| 1795 expect(type.newPrune, isNull); |
| 1796 } |
| 1797 |
| 1798 void test_newPrune_synthetic_typedef() { |
| 1799 // No pruning needs to be done for function types that are associated with |
| 1800 // synthetic typedefs because those types are only created for |
| 1801 // function-typed formal parameters, which can't be directly referred to by |
| 1802 // the user (and hence can't participate in circularities). |
| 1803 FunctionTypeAliasElementImpl f = |
| 1804 ElementFactory.functionTypeAliasElement('f'); |
| 1805 f.synthetic = true; |
| 1806 FunctionTypeImpl type = f.type; |
| 1807 expect(type.newPrune, isNull); |
| 1808 } |
| 1809 |
| 1810 void test_newPrune_with_previous_prune() { |
| 1811 FunctionTypeAliasElementImpl f = |
| 1812 ElementFactory.functionTypeAliasElement('f'); |
| 1813 FunctionTypeAliasElementImpl g = |
| 1814 ElementFactory.functionTypeAliasElement('g'); |
| 1815 FunctionTypeImpl type = f.type; |
| 1816 FunctionTypeImpl prunedType = type.pruned([g]); |
| 1817 List<FunctionTypeAliasElement> pruneList = prunedType.newPrune; |
| 1818 expect(pruneList, hasLength(2)); |
| 1819 expect(pruneList, contains(f)); |
| 1820 expect(pruneList, contains(g)); |
| 1821 } |
| 1822 |
| 1823 void test_normalParameterTypes_pruned_no_type_arguments() { |
| 1824 FunctionTypeAliasElementImpl f = |
| 1825 ElementFactory.functionTypeAliasElement('f'); |
| 1826 FunctionTypeAliasElementImpl g = |
| 1827 ElementFactory.functionTypeAliasElement('g'); |
| 1828 f.parameters = [ElementFactory.requiredParameter2('x', g.type)]; |
| 1829 FunctionTypeImpl paramType = f.type.normalParameterTypes[0]; |
| 1830 expect(paramType.prunedTypedefs, hasLength(1)); |
| 1831 expect(paramType.prunedTypedefs[0], same(f)); |
| 1832 } |
| 1833 |
| 1834 void test_normalParameterTypes_pruned_with_type_arguments() { |
| 1835 FunctionTypeAliasElementImpl f = |
| 1836 ElementFactory.functionTypeAliasElement('f'); |
| 1837 FunctionTypeAliasElementImpl g = |
| 1838 ElementFactory.functionTypeAliasElement('g'); |
| 1839 f.typeParameters = [ElementFactory.typeParameterElement('T')]; |
| 1840 f.parameters = [ElementFactory.requiredParameter2('x', g.type)]; |
| 1841 FunctionTypeImpl paramType = f.type.normalParameterTypes[0]; |
| 1842 expect(paramType.prunedTypedefs, hasLength(1)); |
| 1843 expect(paramType.prunedTypedefs[0], same(f)); |
| 1844 } |
| 1845 |
| 1846 void test_optionalParameterTypes_pruned_no_type_arguments() { |
| 1847 FunctionTypeAliasElementImpl f = |
| 1848 ElementFactory.functionTypeAliasElement('f'); |
| 1849 FunctionTypeAliasElementImpl g = |
| 1850 ElementFactory.functionTypeAliasElement('g'); |
| 1851 f.parameters = [ElementFactory.positionalParameter2('x', g.type)]; |
| 1852 FunctionTypeImpl paramType = f.type.optionalParameterTypes[0]; |
| 1853 expect(paramType.prunedTypedefs, hasLength(1)); |
| 1854 expect(paramType.prunedTypedefs[0], same(f)); |
| 1855 } |
| 1856 |
| 1857 void test_optionalParameterTypes_pruned_with_type_arguments() { |
| 1858 FunctionTypeAliasElementImpl f = |
| 1859 ElementFactory.functionTypeAliasElement('f'); |
| 1860 FunctionTypeAliasElementImpl g = |
| 1861 ElementFactory.functionTypeAliasElement('g'); |
| 1862 f.typeParameters = [ElementFactory.typeParameterElement('T')]; |
| 1863 f.parameters = [ElementFactory.positionalParameter2('x', g.type)]; |
| 1864 FunctionTypeImpl paramType = f.type.optionalParameterTypes[0]; |
| 1865 expect(paramType.prunedTypedefs, hasLength(1)); |
| 1866 expect(paramType.prunedTypedefs[0], same(f)); |
| 1867 } |
| 1868 |
| 1869 void test_returnType_pruned_no_type_arguments() { |
| 1870 FunctionTypeAliasElementImpl f = |
| 1871 ElementFactory.functionTypeAliasElement('f'); |
| 1872 FunctionTypeAliasElementImpl g = |
| 1873 ElementFactory.functionTypeAliasElement('g'); |
| 1874 f.returnType = g.type; |
| 1875 FunctionTypeImpl paramType = f.type.returnType; |
| 1876 expect(paramType.prunedTypedefs, hasLength(1)); |
| 1877 expect(paramType.prunedTypedefs[0], same(f)); |
| 1878 } |
| 1879 |
| 1880 void test_returnType_pruned_with_type_arguments() { |
| 1881 FunctionTypeAliasElementImpl f = |
| 1882 ElementFactory.functionTypeAliasElement('f'); |
| 1883 FunctionTypeAliasElementImpl g = |
| 1884 ElementFactory.functionTypeAliasElement('g'); |
| 1885 f.typeParameters = [ElementFactory.typeParameterElement('T')]; |
| 1886 f.returnType = g.type; |
| 1887 FunctionTypeImpl paramType = f.type.returnType; |
| 1888 expect(paramType.prunedTypedefs, hasLength(1)); |
| 1889 expect(paramType.prunedTypedefs[0], same(f)); |
| 1890 } |
| 1891 |
| 1892 void test_setTypeArguments() { |
| 1893 ClassElementImpl enclosingClass = ElementFactory.classElement2("C", ["E"]); |
| 1894 MethodElementImpl methodElement = |
| 1895 new MethodElementImpl.forNode(AstFactory.identifier3("m")); |
| 1896 enclosingClass.methods = <MethodElement>[methodElement]; |
| 1897 FunctionTypeImpl type = new FunctionTypeImpl(methodElement); |
| 1898 DartType expectedType = enclosingClass.typeParameters[0].type; |
| 1899 type.typeArguments = <DartType>[expectedType]; |
| 1900 List<DartType> arguments = type.typeArguments; |
| 1901 expect(arguments, hasLength(1)); |
| 1902 expect(arguments[0], expectedType); |
| 1903 } |
| 1904 |
| 1905 void test_substitute2_equal() { |
| 1906 ClassElementImpl definingClass = ElementFactory.classElement2("C", ["E"]); |
| 1907 TypeParameterType parameterType = definingClass.typeParameters[0].type; |
| 1908 MethodElementImpl functionElement = |
| 1909 new MethodElementImpl.forNode(AstFactory.identifier3("m")); |
| 1910 String namedParameterName = "c"; |
| 1911 functionElement.parameters = <ParameterElement>[ |
| 1912 ElementFactory.requiredParameter2("a", parameterType), |
| 1913 ElementFactory.positionalParameter2("b", parameterType), |
| 1914 ElementFactory.namedParameter2(namedParameterName, parameterType) |
| 1915 ]; |
| 1916 functionElement.returnType = parameterType; |
| 1917 definingClass.methods = <MethodElement>[functionElement]; |
| 1918 FunctionTypeImpl functionType = new FunctionTypeImpl(functionElement); |
| 1919 functionType.typeArguments = <DartType>[parameterType]; |
| 1920 InterfaceTypeImpl argumentType = new InterfaceTypeImpl( |
| 1921 new ClassElementImpl.forNode(AstFactory.identifier3("D"))); |
| 1922 FunctionType result = functionType.substitute2( |
| 1923 <DartType>[argumentType], <DartType>[parameterType]); |
| 1924 expect(result.returnType, argumentType); |
| 1925 List<DartType> normalParameters = result.normalParameterTypes; |
| 1926 expect(normalParameters, hasLength(1)); |
| 1927 expect(normalParameters[0], argumentType); |
| 1928 List<DartType> optionalParameters = result.optionalParameterTypes; |
| 1929 expect(optionalParameters, hasLength(1)); |
| 1930 expect(optionalParameters[0], argumentType); |
| 1931 Map<String, DartType> namedParameters = result.namedParameterTypes; |
| 1932 expect(namedParameters, hasLength(1)); |
| 1933 expect(namedParameters[namedParameterName], argumentType); |
| 1934 } |
| 1935 |
| 1936 void test_substitute2_notEqual() { |
| 1937 DartType returnType = new InterfaceTypeImpl( |
| 1938 new ClassElementImpl.forNode(AstFactory.identifier3("R"))); |
| 1939 DartType normalParameterType = new InterfaceTypeImpl( |
| 1940 new ClassElementImpl.forNode(AstFactory.identifier3("A"))); |
| 1941 DartType optionalParameterType = new InterfaceTypeImpl( |
| 1942 new ClassElementImpl.forNode(AstFactory.identifier3("B"))); |
| 1943 DartType namedParameterType = new InterfaceTypeImpl( |
| 1944 new ClassElementImpl.forNode(AstFactory.identifier3("C"))); |
| 1945 FunctionElementImpl functionElement = |
| 1946 new FunctionElementImpl.forNode(AstFactory.identifier3("f")); |
| 1947 String namedParameterName = "c"; |
| 1948 functionElement.parameters = <ParameterElement>[ |
| 1949 ElementFactory.requiredParameter2("a", normalParameterType), |
| 1950 ElementFactory.positionalParameter2("b", optionalParameterType), |
| 1951 ElementFactory.namedParameter2(namedParameterName, namedParameterType) |
| 1952 ]; |
| 1953 functionElement.returnType = returnType; |
| 1954 FunctionTypeImpl functionType = new FunctionTypeImpl(functionElement); |
| 1955 InterfaceTypeImpl argumentType = new InterfaceTypeImpl( |
| 1956 new ClassElementImpl.forNode(AstFactory.identifier3("D"))); |
| 1957 TypeParameterTypeImpl parameterType = new TypeParameterTypeImpl( |
| 1958 new TypeParameterElementImpl.forNode(AstFactory.identifier3("E"))); |
| 1959 FunctionType result = functionType.substitute2( |
| 1960 <DartType>[argumentType], <DartType>[parameterType]); |
| 1961 expect(result.returnType, returnType); |
| 1962 List<DartType> normalParameters = result.normalParameterTypes; |
| 1963 expect(normalParameters, hasLength(1)); |
| 1964 expect(normalParameters[0], normalParameterType); |
| 1965 List<DartType> optionalParameters = result.optionalParameterTypes; |
| 1966 expect(optionalParameters, hasLength(1)); |
| 1967 expect(optionalParameters[0], optionalParameterType); |
| 1968 Map<String, DartType> namedParameters = result.namedParameterTypes; |
| 1969 expect(namedParameters, hasLength(1)); |
| 1970 expect(namedParameters[namedParameterName], namedParameterType); |
| 1971 } |
| 1972 |
| 1973 void test_toString_recursive() { |
| 1974 FunctionTypeAliasElementImpl t = |
| 1975 ElementFactory.functionTypeAliasElement("t"); |
| 1976 FunctionTypeAliasElementImpl s = |
| 1977 ElementFactory.functionTypeAliasElement("s"); |
| 1978 t.returnType = s.type; |
| 1979 s.returnType = t.type; |
| 1980 expect(t.type.toString(), '() \u2192 () \u2192 ...'); |
| 1981 } |
| 1982 |
| 1983 void test_toString_recursive_via_interface_type() { |
| 1984 FunctionTypeAliasElementImpl f = |
| 1985 ElementFactory.functionTypeAliasElement('f'); |
| 1986 ClassElementImpl c = ElementFactory.classElement2('C', ['T']); |
| 1987 f.returnType = c.type.substitute4([f.type]); |
| 1988 expect(f.type.toString(), '() \u2192 C<...>'); |
| 1989 } |
| 1990 } |
| 1991 |
| 1992 @reflectiveTest |
| 1993 class HtmlElementImplTest extends EngineTestCase { |
| 1994 void test_equals_differentSource() { |
| 1995 AnalysisContext context = createAnalysisContext(); |
| 1996 HtmlElementImpl elementA = ElementFactory.htmlUnit(context, "indexA.html"); |
| 1997 HtmlElementImpl elementB = ElementFactory.htmlUnit(context, "indexB.html"); |
| 1998 expect(elementA == elementB, isFalse); |
| 1999 } |
| 2000 |
| 2001 void test_equals_null() { |
| 2002 AnalysisContext context = createAnalysisContext(); |
| 2003 HtmlElementImpl element = ElementFactory.htmlUnit(context, "index.html"); |
| 2004 expect(element == null, isFalse); |
| 2005 } |
| 2006 |
| 2007 void test_equals_sameSource() { |
| 2008 AnalysisContext context = createAnalysisContext(); |
| 2009 HtmlElementImpl elementA = ElementFactory.htmlUnit(context, "index.html"); |
| 2010 HtmlElementImpl elementB = ElementFactory.htmlUnit(context, "index.html"); |
| 2011 expect(elementA == elementB, isTrue); |
| 2012 } |
| 2013 |
| 2014 void test_equals_self() { |
| 2015 AnalysisContext context = createAnalysisContext(); |
| 2016 HtmlElementImpl element = ElementFactory.htmlUnit(context, "index.html"); |
| 2017 expect(element == element, isTrue); |
| 2018 } |
| 2019 } |
| 2020 |
| 2021 @reflectiveTest |
| 2022 class InterfaceTypeImplTest extends EngineTestCase { |
| 2023 /** |
| 2024 * The type provider used to access the types. |
| 2025 */ |
| 2026 TestTypeProvider _typeProvider; |
| 2027 |
| 2028 @override |
| 2029 void setUp() { |
| 2030 _typeProvider = new TestTypeProvider(); |
| 2031 } |
| 2032 |
| 2033 void test_computeLongestInheritancePathToObject_multipleInterfacePaths() { |
| 2034 // |
| 2035 // Object |
| 2036 // | |
| 2037 // A |
| 2038 // / \ |
| 2039 // B C |
| 2040 // | | |
| 2041 // | D |
| 2042 // \ / |
| 2043 // E |
| 2044 // |
| 2045 ClassElementImpl classA = ElementFactory.classElement2("A"); |
| 2046 ClassElementImpl classB = ElementFactory.classElement2("B"); |
| 2047 ClassElementImpl classC = ElementFactory.classElement2("C"); |
| 2048 ClassElementImpl classD = ElementFactory.classElement2("D"); |
| 2049 ClassElementImpl classE = ElementFactory.classElement2("E"); |
| 2050 classB.interfaces = <InterfaceType>[classA.type]; |
| 2051 classC.interfaces = <InterfaceType>[classA.type]; |
| 2052 classD.interfaces = <InterfaceType>[classC.type]; |
| 2053 classE.interfaces = <InterfaceType>[classB.type, classD.type]; |
| 2054 // assertion: even though the longest path to Object for typeB is 2, and |
| 2055 // typeE implements typeB, the longest path for typeE is 4 since it also |
| 2056 // implements typeD |
| 2057 expect(InterfaceTypeImpl.computeLongestInheritancePathToObject(classB.type), |
| 2058 2); |
| 2059 expect(InterfaceTypeImpl.computeLongestInheritancePathToObject(classE.type), |
| 2060 4); |
| 2061 } |
| 2062 |
| 2063 void test_computeLongestInheritancePathToObject_multipleSuperclassPaths() { |
| 2064 // |
| 2065 // Object |
| 2066 // | |
| 2067 // A |
| 2068 // / \ |
| 2069 // B C |
| 2070 // | | |
| 2071 // | D |
| 2072 // \ / |
| 2073 // E |
| 2074 // |
| 2075 ClassElement classA = ElementFactory.classElement2("A"); |
| 2076 ClassElement classB = ElementFactory.classElement("B", classA.type); |
| 2077 ClassElement classC = ElementFactory.classElement("C", classA.type); |
| 2078 ClassElement classD = ElementFactory.classElement("D", classC.type); |
| 2079 ClassElementImpl classE = ElementFactory.classElement("E", classB.type); |
| 2080 classE.interfaces = <InterfaceType>[classD.type]; |
| 2081 // assertion: even though the longest path to Object for typeB is 2, and |
| 2082 // typeE extends typeB, the longest path for typeE is 4 since it also |
| 2083 // implements typeD |
| 2084 expect(InterfaceTypeImpl.computeLongestInheritancePathToObject(classB.type), |
| 2085 2); |
| 2086 expect(InterfaceTypeImpl.computeLongestInheritancePathToObject(classE.type), |
| 2087 4); |
| 2088 } |
| 2089 |
| 2090 void test_computeLongestInheritancePathToObject_object() { |
| 2091 // |
| 2092 // Object |
| 2093 // | |
| 2094 // A |
| 2095 // |
| 2096 ClassElement classA = ElementFactory.classElement2("A"); |
| 2097 InterfaceType object = classA.supertype; |
| 2098 expect(InterfaceTypeImpl.computeLongestInheritancePathToObject(object), 0); |
| 2099 } |
| 2100 |
| 2101 void test_computeLongestInheritancePathToObject_recursion() { |
| 2102 ClassElementImpl classA = ElementFactory.classElement2("A"); |
| 2103 ClassElementImpl classB = ElementFactory.classElement("B", classA.type); |
| 2104 classA.supertype = classB.type; |
| 2105 expect(InterfaceTypeImpl.computeLongestInheritancePathToObject(classA.type), |
| 2106 2); |
| 2107 } |
| 2108 |
| 2109 void test_computeLongestInheritancePathToObject_singleInterfacePath() { |
| 2110 // |
| 2111 // Object |
| 2112 // | |
| 2113 // A |
| 2114 // | |
| 2115 // B |
| 2116 // | |
| 2117 // C |
| 2118 // |
| 2119 ClassElementImpl classA = ElementFactory.classElement2("A"); |
| 2120 ClassElementImpl classB = ElementFactory.classElement2("B"); |
| 2121 ClassElementImpl classC = ElementFactory.classElement2("C"); |
| 2122 classB.interfaces = <InterfaceType>[classA.type]; |
| 2123 classC.interfaces = <InterfaceType>[classB.type]; |
| 2124 expect(InterfaceTypeImpl.computeLongestInheritancePathToObject(classA.type), |
| 2125 1); |
| 2126 expect(InterfaceTypeImpl.computeLongestInheritancePathToObject(classB.type), |
| 2127 2); |
| 2128 expect(InterfaceTypeImpl.computeLongestInheritancePathToObject(classC.type), |
| 2129 3); |
| 2130 } |
| 2131 |
| 2132 void test_computeLongestInheritancePathToObject_singleSuperclassPath() { |
| 2133 // |
| 2134 // Object |
| 2135 // | |
| 2136 // A |
| 2137 // | |
| 2138 // B |
| 2139 // | |
| 2140 // C |
| 2141 // |
| 2142 ClassElement classA = ElementFactory.classElement2("A"); |
| 2143 ClassElement classB = ElementFactory.classElement("B", classA.type); |
| 2144 ClassElement classC = ElementFactory.classElement("C", classB.type); |
| 2145 expect(InterfaceTypeImpl.computeLongestInheritancePathToObject(classA.type), |
| 2146 1); |
| 2147 expect(InterfaceTypeImpl.computeLongestInheritancePathToObject(classB.type), |
| 2148 2); |
| 2149 expect(InterfaceTypeImpl.computeLongestInheritancePathToObject(classC.type), |
| 2150 3); |
| 2151 } |
| 2152 |
| 2153 void test_computeSuperinterfaceSet_genericInterfacePath() { |
| 2154 // |
| 2155 // A |
| 2156 // | implements |
| 2157 // B<T> |
| 2158 // | implements |
| 2159 // C<T> |
| 2160 // |
| 2161 // D |
| 2162 // |
| 2163 ClassElementImpl classA = ElementFactory.classElement2("A"); |
| 2164 ClassElementImpl classB = ElementFactory.classElement2("B", ["T"]); |
| 2165 ClassElementImpl classC = ElementFactory.classElement2("C", ["T"]); |
| 2166 ClassElement classD = ElementFactory.classElement2("D"); |
| 2167 InterfaceType typeA = classA.type; |
| 2168 classB.interfaces = <InterfaceType>[typeA]; |
| 2169 InterfaceTypeImpl typeBT = new InterfaceTypeImpl(classB); |
| 2170 DartType typeT = classC.type.typeArguments[0]; |
| 2171 typeBT.typeArguments = <DartType>[typeT]; |
| 2172 classC.interfaces = <InterfaceType>[typeBT]; |
| 2173 // A |
| 2174 Set<InterfaceType> superinterfacesOfA = |
| 2175 InterfaceTypeImpl.computeSuperinterfaceSet(typeA); |
| 2176 expect(superinterfacesOfA, hasLength(1)); |
| 2177 InterfaceType typeObject = ElementFactory.object.type; |
| 2178 expect(superinterfacesOfA.contains(typeObject), isTrue); |
| 2179 // B<D> |
| 2180 InterfaceTypeImpl typeBD = new InterfaceTypeImpl(classB); |
| 2181 typeBD.typeArguments = <DartType>[classD.type]; |
| 2182 Set<InterfaceType> superinterfacesOfBD = |
| 2183 InterfaceTypeImpl.computeSuperinterfaceSet(typeBD); |
| 2184 expect(superinterfacesOfBD, hasLength(2)); |
| 2185 expect(superinterfacesOfBD.contains(typeObject), isTrue); |
| 2186 expect(superinterfacesOfBD.contains(typeA), isTrue); |
| 2187 // C<D> |
| 2188 InterfaceTypeImpl typeCD = new InterfaceTypeImpl(classC); |
| 2189 typeCD.typeArguments = <DartType>[classD.type]; |
| 2190 Set<InterfaceType> superinterfacesOfCD = |
| 2191 InterfaceTypeImpl.computeSuperinterfaceSet(typeCD); |
| 2192 expect(superinterfacesOfCD, hasLength(3)); |
| 2193 expect(superinterfacesOfCD.contains(typeObject), isTrue); |
| 2194 expect(superinterfacesOfCD.contains(typeA), isTrue); |
| 2195 expect(superinterfacesOfCD.contains(typeBD), isTrue); |
| 2196 } |
| 2197 |
| 2198 void test_computeSuperinterfaceSet_genericSuperclassPath() { |
| 2199 // |
| 2200 // A |
| 2201 // | |
| 2202 // B<T> |
| 2203 // | |
| 2204 // C<T> |
| 2205 // |
| 2206 // D |
| 2207 // |
| 2208 ClassElement classA = ElementFactory.classElement2("A"); |
| 2209 InterfaceType typeA = classA.type; |
| 2210 ClassElement classB = ElementFactory.classElement("B", typeA, ["T"]); |
| 2211 ClassElementImpl classC = ElementFactory.classElement2("C", ["T"]); |
| 2212 InterfaceTypeImpl typeBT = new InterfaceTypeImpl(classB); |
| 2213 DartType typeT = classC.type.typeArguments[0]; |
| 2214 typeBT.typeArguments = <DartType>[typeT]; |
| 2215 classC.supertype = typeBT; |
| 2216 ClassElement classD = ElementFactory.classElement2("D"); |
| 2217 // A |
| 2218 Set<InterfaceType> superinterfacesOfA = |
| 2219 InterfaceTypeImpl.computeSuperinterfaceSet(typeA); |
| 2220 expect(superinterfacesOfA, hasLength(1)); |
| 2221 InterfaceType typeObject = ElementFactory.object.type; |
| 2222 expect(superinterfacesOfA.contains(typeObject), isTrue); |
| 2223 // B<D> |
| 2224 InterfaceTypeImpl typeBD = new InterfaceTypeImpl(classB); |
| 2225 typeBD.typeArguments = <DartType>[classD.type]; |
| 2226 Set<InterfaceType> superinterfacesOfBD = |
| 2227 InterfaceTypeImpl.computeSuperinterfaceSet(typeBD); |
| 2228 expect(superinterfacesOfBD, hasLength(2)); |
| 2229 expect(superinterfacesOfBD.contains(typeObject), isTrue); |
| 2230 expect(superinterfacesOfBD.contains(typeA), isTrue); |
| 2231 // C<D> |
| 2232 InterfaceTypeImpl typeCD = new InterfaceTypeImpl(classC); |
| 2233 typeCD.typeArguments = <DartType>[classD.type]; |
| 2234 Set<InterfaceType> superinterfacesOfCD = |
| 2235 InterfaceTypeImpl.computeSuperinterfaceSet(typeCD); |
| 2236 expect(superinterfacesOfCD, hasLength(3)); |
| 2237 expect(superinterfacesOfCD.contains(typeObject), isTrue); |
| 2238 expect(superinterfacesOfCD.contains(typeA), isTrue); |
| 2239 expect(superinterfacesOfCD.contains(typeBD), isTrue); |
| 2240 } |
| 2241 |
| 2242 void test_computeSuperinterfaceSet_multipleInterfacePaths() { |
| 2243 ClassElementImpl classA = ElementFactory.classElement2("A"); |
| 2244 ClassElementImpl classB = ElementFactory.classElement2("B"); |
| 2245 ClassElementImpl classC = ElementFactory.classElement2("C"); |
| 2246 ClassElementImpl classD = ElementFactory.classElement2("D"); |
| 2247 ClassElementImpl classE = ElementFactory.classElement2("E"); |
| 2248 classB.interfaces = <InterfaceType>[classA.type]; |
| 2249 classC.interfaces = <InterfaceType>[classA.type]; |
| 2250 classD.interfaces = <InterfaceType>[classC.type]; |
| 2251 classE.interfaces = <InterfaceType>[classB.type, classD.type]; |
| 2252 // D |
| 2253 Set<InterfaceType> superinterfacesOfD = |
| 2254 InterfaceTypeImpl.computeSuperinterfaceSet(classD.type); |
| 2255 expect(superinterfacesOfD, hasLength(3)); |
| 2256 expect(superinterfacesOfD.contains(ElementFactory.object.type), isTrue); |
| 2257 expect(superinterfacesOfD.contains(classA.type), isTrue); |
| 2258 expect(superinterfacesOfD.contains(classC.type), isTrue); |
| 2259 // E |
| 2260 Set<InterfaceType> superinterfacesOfE = |
| 2261 InterfaceTypeImpl.computeSuperinterfaceSet(classE.type); |
| 2262 expect(superinterfacesOfE, hasLength(5)); |
| 2263 expect(superinterfacesOfE.contains(ElementFactory.object.type), isTrue); |
| 2264 expect(superinterfacesOfE.contains(classA.type), isTrue); |
| 2265 expect(superinterfacesOfE.contains(classB.type), isTrue); |
| 2266 expect(superinterfacesOfE.contains(classC.type), isTrue); |
| 2267 expect(superinterfacesOfE.contains(classD.type), isTrue); |
| 2268 } |
| 2269 |
| 2270 void test_computeSuperinterfaceSet_multipleSuperclassPaths() { |
| 2271 ClassElement classA = ElementFactory.classElement2("A"); |
| 2272 ClassElement classB = ElementFactory.classElement("B", classA.type); |
| 2273 ClassElement classC = ElementFactory.classElement("C", classA.type); |
| 2274 ClassElement classD = ElementFactory.classElement("D", classC.type); |
| 2275 ClassElementImpl classE = ElementFactory.classElement("E", classB.type); |
| 2276 classE.interfaces = <InterfaceType>[classD.type]; |
| 2277 // D |
| 2278 Set<InterfaceType> superinterfacesOfD = |
| 2279 InterfaceTypeImpl.computeSuperinterfaceSet(classD.type); |
| 2280 expect(superinterfacesOfD, hasLength(3)); |
| 2281 expect(superinterfacesOfD.contains(ElementFactory.object.type), isTrue); |
| 2282 expect(superinterfacesOfD.contains(classA.type), isTrue); |
| 2283 expect(superinterfacesOfD.contains(classC.type), isTrue); |
| 2284 // E |
| 2285 Set<InterfaceType> superinterfacesOfE = |
| 2286 InterfaceTypeImpl.computeSuperinterfaceSet(classE.type); |
| 2287 expect(superinterfacesOfE, hasLength(5)); |
| 2288 expect(superinterfacesOfE.contains(ElementFactory.object.type), isTrue); |
| 2289 expect(superinterfacesOfE.contains(classA.type), isTrue); |
| 2290 expect(superinterfacesOfE.contains(classB.type), isTrue); |
| 2291 expect(superinterfacesOfE.contains(classC.type), isTrue); |
| 2292 expect(superinterfacesOfE.contains(classD.type), isTrue); |
| 2293 } |
| 2294 |
| 2295 void test_computeSuperinterfaceSet_recursion() { |
| 2296 ClassElementImpl classA = ElementFactory.classElement2("A"); |
| 2297 ClassElementImpl classB = ElementFactory.classElement("B", classA.type); |
| 2298 classA.supertype = classB.type; |
| 2299 Set<InterfaceType> superinterfacesOfB = |
| 2300 InterfaceTypeImpl.computeSuperinterfaceSet(classB.type); |
| 2301 expect(superinterfacesOfB, hasLength(2)); |
| 2302 } |
| 2303 |
| 2304 void test_computeSuperinterfaceSet_singleInterfacePath() { |
| 2305 ClassElementImpl classA = ElementFactory.classElement2("A"); |
| 2306 ClassElementImpl classB = ElementFactory.classElement2("B"); |
| 2307 ClassElementImpl classC = ElementFactory.classElement2("C"); |
| 2308 classB.interfaces = <InterfaceType>[classA.type]; |
| 2309 classC.interfaces = <InterfaceType>[classB.type]; |
| 2310 // A |
| 2311 Set<InterfaceType> superinterfacesOfA = |
| 2312 InterfaceTypeImpl.computeSuperinterfaceSet(classA.type); |
| 2313 expect(superinterfacesOfA, hasLength(1)); |
| 2314 expect(superinterfacesOfA.contains(ElementFactory.object.type), isTrue); |
| 2315 // B |
| 2316 Set<InterfaceType> superinterfacesOfB = |
| 2317 InterfaceTypeImpl.computeSuperinterfaceSet(classB.type); |
| 2318 expect(superinterfacesOfB, hasLength(2)); |
| 2319 expect(superinterfacesOfB.contains(ElementFactory.object.type), isTrue); |
| 2320 expect(superinterfacesOfB.contains(classA.type), isTrue); |
| 2321 // C |
| 2322 Set<InterfaceType> superinterfacesOfC = |
| 2323 InterfaceTypeImpl.computeSuperinterfaceSet(classC.type); |
| 2324 expect(superinterfacesOfC, hasLength(3)); |
| 2325 expect(superinterfacesOfC.contains(ElementFactory.object.type), isTrue); |
| 2326 expect(superinterfacesOfC.contains(classA.type), isTrue); |
| 2327 expect(superinterfacesOfC.contains(classB.type), isTrue); |
| 2328 } |
| 2329 |
| 2330 void test_computeSuperinterfaceSet_singleSuperclassPath() { |
| 2331 // |
| 2332 // A |
| 2333 // | |
| 2334 // B |
| 2335 // | |
| 2336 // C |
| 2337 // |
| 2338 ClassElement classA = ElementFactory.classElement2("A"); |
| 2339 ClassElement classB = ElementFactory.classElement("B", classA.type); |
| 2340 ClassElement classC = ElementFactory.classElement("C", classB.type); |
| 2341 // A |
| 2342 Set<InterfaceType> superinterfacesOfA = |
| 2343 InterfaceTypeImpl.computeSuperinterfaceSet(classA.type); |
| 2344 expect(superinterfacesOfA, hasLength(1)); |
| 2345 expect(superinterfacesOfA.contains(ElementFactory.object.type), isTrue); |
| 2346 // B |
| 2347 Set<InterfaceType> superinterfacesOfB = |
| 2348 InterfaceTypeImpl.computeSuperinterfaceSet(classB.type); |
| 2349 expect(superinterfacesOfB, hasLength(2)); |
| 2350 expect(superinterfacesOfB.contains(ElementFactory.object.type), isTrue); |
| 2351 expect(superinterfacesOfB.contains(classA.type), isTrue); |
| 2352 // C |
| 2353 Set<InterfaceType> superinterfacesOfC = |
| 2354 InterfaceTypeImpl.computeSuperinterfaceSet(classC.type); |
| 2355 expect(superinterfacesOfC, hasLength(3)); |
| 2356 expect(superinterfacesOfC.contains(ElementFactory.object.type), isTrue); |
| 2357 expect(superinterfacesOfC.contains(classA.type), isTrue); |
| 2358 expect(superinterfacesOfC.contains(classB.type), isTrue); |
| 2359 } |
| 2360 |
| 2361 void test_creation() { |
| 2362 expect(new InterfaceTypeImpl(ElementFactory.classElement2("A")), isNotNull); |
| 2363 } |
| 2364 |
| 2365 void test_getAccessors() { |
| 2366 ClassElementImpl typeElement = ElementFactory.classElement2("A"); |
| 2367 PropertyAccessorElement getterG = |
| 2368 ElementFactory.getterElement("g", false, null); |
| 2369 PropertyAccessorElement getterH = |
| 2370 ElementFactory.getterElement("h", false, null); |
| 2371 typeElement.accessors = <PropertyAccessorElement>[getterG, getterH]; |
| 2372 InterfaceTypeImpl type = new InterfaceTypeImpl(typeElement); |
| 2373 expect(type.accessors.length, 2); |
| 2374 } |
| 2375 |
| 2376 void test_getAccessors_empty() { |
| 2377 ClassElementImpl typeElement = ElementFactory.classElement2("A"); |
| 2378 InterfaceTypeImpl type = new InterfaceTypeImpl(typeElement); |
| 2379 expect(type.accessors.length, 0); |
| 2380 } |
| 2381 |
| 2382 void test_getConstructors() { |
| 2383 ClassElementImpl typeElement = ElementFactory.classElement2("A"); |
| 2384 ConstructorElementImpl constructorOne = |
| 2385 ElementFactory.constructorElement(typeElement, 'one', false); |
| 2386 ConstructorElementImpl constructorTwo = |
| 2387 ElementFactory.constructorElement(typeElement, 'two', false); |
| 2388 typeElement.constructors = <ConstructorElement>[ |
| 2389 constructorOne, |
| 2390 constructorTwo |
| 2391 ]; |
| 2392 InterfaceTypeImpl type = new InterfaceTypeImpl(typeElement); |
| 2393 expect(type.constructors, hasLength(2)); |
| 2394 } |
| 2395 |
| 2396 void test_getConstructors_empty() { |
| 2397 ClassElementImpl typeElement = ElementFactory.classElement2("A"); |
| 2398 typeElement.constructors = ConstructorElement.EMPTY_LIST; |
| 2399 InterfaceTypeImpl type = new InterfaceTypeImpl(typeElement); |
| 2400 expect(type.constructors, isEmpty); |
| 2401 } |
| 2402 |
| 2403 void test_getElement() { |
| 2404 ClassElementImpl typeElement = ElementFactory.classElement2("A"); |
| 2405 InterfaceTypeImpl type = new InterfaceTypeImpl(typeElement); |
| 2406 expect(type.element, typeElement); |
| 2407 } |
| 2408 |
| 2409 void test_getGetter_implemented() { |
| 2410 // |
| 2411 // class A { g {} } |
| 2412 // |
| 2413 ClassElementImpl classA = ElementFactory.classElement2("A"); |
| 2414 String getterName = "g"; |
| 2415 PropertyAccessorElement getterG = |
| 2416 ElementFactory.getterElement(getterName, false, null); |
| 2417 classA.accessors = <PropertyAccessorElement>[getterG]; |
| 2418 InterfaceType typeA = classA.type; |
| 2419 expect(typeA.getGetter(getterName), same(getterG)); |
| 2420 } |
| 2421 |
| 2422 void test_getGetter_parameterized() { |
| 2423 // |
| 2424 // class A<E> { E get g {} } |
| 2425 // |
| 2426 ClassElementImpl classA = ElementFactory.classElement2("A", ["E"]); |
| 2427 DartType typeE = classA.type.typeArguments[0]; |
| 2428 String getterName = "g"; |
| 2429 PropertyAccessorElement getterG = |
| 2430 ElementFactory.getterElement(getterName, false, typeE); |
| 2431 classA.accessors = <PropertyAccessorElement>[getterG]; |
| 2432 (getterG.type as FunctionTypeImpl).typeArguments = |
| 2433 classA.type.typeArguments; |
| 2434 // |
| 2435 // A<I> |
| 2436 // |
| 2437 InterfaceType typeI = ElementFactory.classElement2("I").type; |
| 2438 InterfaceTypeImpl typeAI = new InterfaceTypeImpl(classA); |
| 2439 typeAI.typeArguments = <DartType>[typeI]; |
| 2440 PropertyAccessorElement getter = typeAI.getGetter(getterName); |
| 2441 expect(getter, isNotNull); |
| 2442 FunctionType getterType = getter.type; |
| 2443 expect(getterType.returnType, same(typeI)); |
| 2444 } |
| 2445 |
| 2446 void test_getGetter_unimplemented() { |
| 2447 // |
| 2448 // class A {} |
| 2449 // |
| 2450 ClassElementImpl classA = ElementFactory.classElement2("A"); |
| 2451 InterfaceType typeA = classA.type; |
| 2452 expect(typeA.getGetter("g"), isNull); |
| 2453 } |
| 2454 |
| 2455 void test_getInterfaces_nonParameterized() { |
| 2456 // |
| 2457 // class C implements A, B |
| 2458 // |
| 2459 ClassElementImpl classA = ElementFactory.classElement2("A"); |
| 2460 InterfaceType typeA = classA.type; |
| 2461 ClassElementImpl classB = ElementFactory.classElement2("B"); |
| 2462 InterfaceType typeB = classB.type; |
| 2463 ClassElementImpl classC = ElementFactory.classElement2("C"); |
| 2464 classC.interfaces = <InterfaceType>[typeA, typeB]; |
| 2465 List<InterfaceType> interfaces = classC.type.interfaces; |
| 2466 expect(interfaces, hasLength(2)); |
| 2467 if (identical(interfaces[0], typeA)) { |
| 2468 expect(interfaces[1], same(typeB)); |
| 2469 } else { |
| 2470 expect(interfaces[0], same(typeB)); |
| 2471 expect(interfaces[1], same(typeA)); |
| 2472 } |
| 2473 } |
| 2474 |
| 2475 void test_getInterfaces_parameterized() { |
| 2476 // |
| 2477 // class A<E> |
| 2478 // class B<F> implements A<F> |
| 2479 // |
| 2480 ClassElementImpl classA = ElementFactory.classElement2("A", ["E"]); |
| 2481 ClassElementImpl classB = ElementFactory.classElement2("B", ["F"]); |
| 2482 InterfaceType typeB = classB.type; |
| 2483 InterfaceTypeImpl typeAF = new InterfaceTypeImpl(classA); |
| 2484 typeAF.typeArguments = <DartType>[typeB.typeArguments[0]]; |
| 2485 classB.interfaces = <InterfaceType>[typeAF]; |
| 2486 // |
| 2487 // B<I> |
| 2488 // |
| 2489 InterfaceType typeI = ElementFactory.classElement2("I").type; |
| 2490 InterfaceTypeImpl typeBI = new InterfaceTypeImpl(classB); |
| 2491 typeBI.typeArguments = <DartType>[typeI]; |
| 2492 List<InterfaceType> interfaces = typeBI.interfaces; |
| 2493 expect(interfaces, hasLength(1)); |
| 2494 InterfaceType result = interfaces[0]; |
| 2495 expect(result.element, same(classA)); |
| 2496 expect(result.typeArguments[0], same(typeI)); |
| 2497 } |
| 2498 |
| 2499 void test_getLeastUpperBound_directInterfaceCase() { |
| 2500 // |
| 2501 // class A |
| 2502 // class B implements A |
| 2503 // class C implements B |
| 2504 // |
| 2505 ClassElementImpl classA = ElementFactory.classElement2("A"); |
| 2506 ClassElementImpl classB = ElementFactory.classElement2("B"); |
| 2507 ClassElementImpl classC = ElementFactory.classElement2("C"); |
| 2508 InterfaceType typeA = classA.type; |
| 2509 InterfaceType typeB = classB.type; |
| 2510 InterfaceType typeC = classC.type; |
| 2511 classB.interfaces = <InterfaceType>[typeA]; |
| 2512 classC.interfaces = <InterfaceType>[typeB]; |
| 2513 expect(typeB.getLeastUpperBound(typeC), typeB); |
| 2514 expect(typeC.getLeastUpperBound(typeB), typeB); |
| 2515 } |
| 2516 |
| 2517 void test_getLeastUpperBound_directSubclassCase() { |
| 2518 // |
| 2519 // class A |
| 2520 // class B extends A |
| 2521 // class C extends B |
| 2522 // |
| 2523 ClassElementImpl classA = ElementFactory.classElement2("A"); |
| 2524 ClassElementImpl classB = ElementFactory.classElement("B", classA.type); |
| 2525 ClassElementImpl classC = ElementFactory.classElement("C", classB.type); |
| 2526 InterfaceType typeB = classB.type; |
| 2527 InterfaceType typeC = classC.type; |
| 2528 expect(typeB.getLeastUpperBound(typeC), typeB); |
| 2529 expect(typeC.getLeastUpperBound(typeB), typeB); |
| 2530 } |
| 2531 |
| 2532 void test_getLeastUpperBound_functionType() { |
| 2533 DartType interfaceType = ElementFactory.classElement2("A").type; |
| 2534 FunctionTypeImpl functionType = new FunctionTypeImpl( |
| 2535 new FunctionElementImpl.forNode(AstFactory.identifier3("f"))); |
| 2536 expect(interfaceType.getLeastUpperBound(functionType), isNull); |
| 2537 } |
| 2538 |
| 2539 void test_getLeastUpperBound_mixinCase() { |
| 2540 // |
| 2541 // class A |
| 2542 // class B extends A |
| 2543 // class C extends A |
| 2544 // class D extends B with M, N, O, P |
| 2545 // |
| 2546 ClassElement classA = ElementFactory.classElement2("A"); |
| 2547 ClassElement classB = ElementFactory.classElement("B", classA.type); |
| 2548 ClassElement classC = ElementFactory.classElement("C", classA.type); |
| 2549 ClassElementImpl classD = ElementFactory.classElement("D", classB.type); |
| 2550 InterfaceType typeA = classA.type; |
| 2551 InterfaceType typeC = classC.type; |
| 2552 InterfaceType typeD = classD.type; |
| 2553 classD.mixins = <InterfaceType>[ |
| 2554 ElementFactory.classElement2("M").type, |
| 2555 ElementFactory.classElement2("N").type, |
| 2556 ElementFactory.classElement2("O").type, |
| 2557 ElementFactory.classElement2("P").type |
| 2558 ]; |
| 2559 expect(typeD.getLeastUpperBound(typeC), typeA); |
| 2560 expect(typeC.getLeastUpperBound(typeD), typeA); |
| 2561 } |
| 2562 |
| 2563 void test_getLeastUpperBound_null() { |
| 2564 DartType interfaceType = ElementFactory.classElement2("A").type; |
| 2565 expect(interfaceType.getLeastUpperBound(null), isNull); |
| 2566 } |
| 2567 |
| 2568 void test_getLeastUpperBound_object() { |
| 2569 ClassElementImpl classA = ElementFactory.classElement2("A"); |
| 2570 ClassElementImpl classB = ElementFactory.classElement2("B"); |
| 2571 InterfaceType typeA = classA.type; |
| 2572 InterfaceType typeB = classB.type; |
| 2573 DartType typeObject = typeA.element.supertype; |
| 2574 // assert that object does not have a super type |
| 2575 expect((typeObject.element as ClassElement).supertype, isNull); |
| 2576 // assert that both A and B have the same super type of Object |
| 2577 expect(typeB.element.supertype, typeObject); |
| 2578 // finally, assert that the only least upper bound of A and B is Object |
| 2579 expect(typeA.getLeastUpperBound(typeB), typeObject); |
| 2580 } |
| 2581 |
| 2582 void test_getLeastUpperBound_self() { |
| 2583 ClassElement classA = ElementFactory.classElement2("A"); |
| 2584 InterfaceType typeA = classA.type; |
| 2585 expect(typeA.getLeastUpperBound(typeA), typeA); |
| 2586 } |
| 2587 |
| 2588 void test_getLeastUpperBound_sharedSuperclass1() { |
| 2589 ClassElementImpl classA = ElementFactory.classElement2("A"); |
| 2590 ClassElementImpl classB = ElementFactory.classElement("B", classA.type); |
| 2591 ClassElementImpl classC = ElementFactory.classElement("C", classA.type); |
| 2592 InterfaceType typeA = classA.type; |
| 2593 InterfaceType typeB = classB.type; |
| 2594 InterfaceType typeC = classC.type; |
| 2595 expect(typeB.getLeastUpperBound(typeC), typeA); |
| 2596 expect(typeC.getLeastUpperBound(typeB), typeA); |
| 2597 } |
| 2598 |
| 2599 void test_getLeastUpperBound_sharedSuperclass2() { |
| 2600 ClassElementImpl classA = ElementFactory.classElement2("A"); |
| 2601 ClassElementImpl classB = ElementFactory.classElement("B", classA.type); |
| 2602 ClassElementImpl classC = ElementFactory.classElement("C", classA.type); |
| 2603 ClassElementImpl classD = ElementFactory.classElement("D", classC.type); |
| 2604 InterfaceType typeA = classA.type; |
| 2605 InterfaceType typeB = classB.type; |
| 2606 InterfaceType typeD = classD.type; |
| 2607 expect(typeB.getLeastUpperBound(typeD), typeA); |
| 2608 expect(typeD.getLeastUpperBound(typeB), typeA); |
| 2609 } |
| 2610 |
| 2611 void test_getLeastUpperBound_sharedSuperclass3() { |
| 2612 ClassElementImpl classA = ElementFactory.classElement2("A"); |
| 2613 ClassElementImpl classB = ElementFactory.classElement("B", classA.type); |
| 2614 ClassElementImpl classC = ElementFactory.classElement("C", classB.type); |
| 2615 ClassElementImpl classD = ElementFactory.classElement("D", classB.type); |
| 2616 InterfaceType typeB = classB.type; |
| 2617 InterfaceType typeC = classC.type; |
| 2618 InterfaceType typeD = classD.type; |
| 2619 expect(typeC.getLeastUpperBound(typeD), typeB); |
| 2620 expect(typeD.getLeastUpperBound(typeC), typeB); |
| 2621 } |
| 2622 |
| 2623 void test_getLeastUpperBound_sharedSuperclass4() { |
| 2624 ClassElement classA = ElementFactory.classElement2("A"); |
| 2625 ClassElement classA2 = ElementFactory.classElement2("A2"); |
| 2626 ClassElement classA3 = ElementFactory.classElement2("A3"); |
| 2627 ClassElementImpl classB = ElementFactory.classElement("B", classA.type); |
| 2628 ClassElementImpl classC = ElementFactory.classElement("C", classA.type); |
| 2629 InterfaceType typeA = classA.type; |
| 2630 InterfaceType typeA2 = classA2.type; |
| 2631 InterfaceType typeA3 = classA3.type; |
| 2632 InterfaceType typeB = classB.type; |
| 2633 InterfaceType typeC = classC.type; |
| 2634 classB.interfaces = <InterfaceType>[typeA2]; |
| 2635 classC.interfaces = <InterfaceType>[typeA3]; |
| 2636 expect(typeB.getLeastUpperBound(typeC), typeA); |
| 2637 expect(typeC.getLeastUpperBound(typeB), typeA); |
| 2638 } |
| 2639 |
| 2640 void test_getLeastUpperBound_sharedSuperinterface1() { |
| 2641 ClassElementImpl classA = ElementFactory.classElement2("A"); |
| 2642 ClassElementImpl classB = ElementFactory.classElement2("B"); |
| 2643 ClassElementImpl classC = ElementFactory.classElement2("C"); |
| 2644 InterfaceType typeA = classA.type; |
| 2645 InterfaceType typeB = classB.type; |
| 2646 InterfaceType typeC = classC.type; |
| 2647 classB.interfaces = <InterfaceType>[typeA]; |
| 2648 classC.interfaces = <InterfaceType>[typeA]; |
| 2649 expect(typeB.getLeastUpperBound(typeC), typeA); |
| 2650 expect(typeC.getLeastUpperBound(typeB), typeA); |
| 2651 } |
| 2652 |
| 2653 void test_getLeastUpperBound_sharedSuperinterface2() { |
| 2654 ClassElementImpl classA = ElementFactory.classElement2("A"); |
| 2655 ClassElementImpl classB = ElementFactory.classElement2("B"); |
| 2656 ClassElementImpl classC = ElementFactory.classElement2("C"); |
| 2657 ClassElementImpl classD = ElementFactory.classElement2("D"); |
| 2658 InterfaceType typeA = classA.type; |
| 2659 InterfaceType typeB = classB.type; |
| 2660 InterfaceType typeC = classC.type; |
| 2661 InterfaceType typeD = classD.type; |
| 2662 classB.interfaces = <InterfaceType>[typeA]; |
| 2663 classC.interfaces = <InterfaceType>[typeA]; |
| 2664 classD.interfaces = <InterfaceType>[typeC]; |
| 2665 expect(typeB.getLeastUpperBound(typeD), typeA); |
| 2666 expect(typeD.getLeastUpperBound(typeB), typeA); |
| 2667 } |
| 2668 |
| 2669 void test_getLeastUpperBound_sharedSuperinterface3() { |
| 2670 ClassElementImpl classA = ElementFactory.classElement2("A"); |
| 2671 ClassElementImpl classB = ElementFactory.classElement2("B"); |
| 2672 ClassElementImpl classC = ElementFactory.classElement2("C"); |
| 2673 ClassElementImpl classD = ElementFactory.classElement2("D"); |
| 2674 InterfaceType typeA = classA.type; |
| 2675 InterfaceType typeB = classB.type; |
| 2676 InterfaceType typeC = classC.type; |
| 2677 InterfaceType typeD = classD.type; |
| 2678 classB.interfaces = <InterfaceType>[typeA]; |
| 2679 classC.interfaces = <InterfaceType>[typeB]; |
| 2680 classD.interfaces = <InterfaceType>[typeB]; |
| 2681 expect(typeC.getLeastUpperBound(typeD), typeB); |
| 2682 expect(typeD.getLeastUpperBound(typeC), typeB); |
| 2683 } |
| 2684 |
| 2685 void test_getLeastUpperBound_sharedSuperinterface4() { |
| 2686 ClassElement classA = ElementFactory.classElement2("A"); |
| 2687 ClassElement classA2 = ElementFactory.classElement2("A2"); |
| 2688 ClassElement classA3 = ElementFactory.classElement2("A3"); |
| 2689 ClassElementImpl classB = ElementFactory.classElement2("B"); |
| 2690 ClassElementImpl classC = ElementFactory.classElement2("C"); |
| 2691 InterfaceType typeA = classA.type; |
| 2692 InterfaceType typeA2 = classA2.type; |
| 2693 InterfaceType typeA3 = classA3.type; |
| 2694 InterfaceType typeB = classB.type; |
| 2695 InterfaceType typeC = classC.type; |
| 2696 classB.interfaces = <InterfaceType>[typeA, typeA2]; |
| 2697 classC.interfaces = <InterfaceType>[typeA, typeA3]; |
| 2698 expect(typeB.getLeastUpperBound(typeC), typeA); |
| 2699 expect(typeC.getLeastUpperBound(typeB), typeA); |
| 2700 } |
| 2701 |
| 2702 void test_getLeastUpperBound_twoComparables() { |
| 2703 InterfaceType string = _typeProvider.stringType; |
| 2704 InterfaceType num = _typeProvider.numType; |
| 2705 expect(string.getLeastUpperBound(num), _typeProvider.objectType); |
| 2706 } |
| 2707 |
| 2708 void test_getLeastUpperBound_typeParameters_different() { |
| 2709 // |
| 2710 // class List<int> |
| 2711 // class List<double> |
| 2712 // |
| 2713 InterfaceType listType = _typeProvider.listType; |
| 2714 InterfaceType intType = _typeProvider.intType; |
| 2715 InterfaceType doubleType = _typeProvider.doubleType; |
| 2716 InterfaceType listOfIntType = listType.substitute4(<DartType>[intType]); |
| 2717 InterfaceType listOfDoubleType = |
| 2718 listType.substitute4(<DartType>[doubleType]); |
| 2719 expect(listOfIntType.getLeastUpperBound(listOfDoubleType), |
| 2720 _typeProvider.objectType); |
| 2721 } |
| 2722 |
| 2723 void test_getLeastUpperBound_typeParameters_same() { |
| 2724 // |
| 2725 // List<int> |
| 2726 // List<int> |
| 2727 // |
| 2728 InterfaceType listType = _typeProvider.listType; |
| 2729 InterfaceType intType = _typeProvider.intType; |
| 2730 InterfaceType listOfIntType = listType.substitute4(<DartType>[intType]); |
| 2731 expect(listOfIntType.getLeastUpperBound(listOfIntType), listOfIntType); |
| 2732 } |
| 2733 |
| 2734 void test_getMethod_implemented() { |
| 2735 // |
| 2736 // class A { m() {} } |
| 2737 // |
| 2738 ClassElementImpl classA = ElementFactory.classElement2("A"); |
| 2739 String methodName = "m"; |
| 2740 MethodElementImpl methodM = ElementFactory.methodElement(methodName, null); |
| 2741 classA.methods = <MethodElement>[methodM]; |
| 2742 InterfaceType typeA = classA.type; |
| 2743 expect(typeA.getMethod(methodName), same(methodM)); |
| 2744 } |
| 2745 |
| 2746 void test_getMethod_parameterized() { |
| 2747 // |
| 2748 // class A<E> { E m(E p) {} } |
| 2749 // |
| 2750 ClassElementImpl classA = ElementFactory.classElement2("A", ["E"]); |
| 2751 DartType typeE = classA.type.typeArguments[0]; |
| 2752 String methodName = "m"; |
| 2753 MethodElementImpl methodM = |
| 2754 ElementFactory.methodElement(methodName, typeE, [typeE]); |
| 2755 classA.methods = <MethodElement>[methodM]; |
| 2756 (methodM.type as FunctionTypeImpl).typeArguments = |
| 2757 classA.type.typeArguments; |
| 2758 // |
| 2759 // A<I> |
| 2760 // |
| 2761 InterfaceType typeI = ElementFactory.classElement2("I").type; |
| 2762 InterfaceTypeImpl typeAI = new InterfaceTypeImpl(classA); |
| 2763 typeAI.typeArguments = <DartType>[typeI]; |
| 2764 MethodElement method = typeAI.getMethod(methodName); |
| 2765 expect(method, isNotNull); |
| 2766 FunctionType methodType = method.type; |
| 2767 expect(methodType.returnType, same(typeI)); |
| 2768 List<DartType> parameterTypes = methodType.normalParameterTypes; |
| 2769 expect(parameterTypes, hasLength(1)); |
| 2770 expect(parameterTypes[0], same(typeI)); |
| 2771 } |
| 2772 |
| 2773 void test_getMethod_unimplemented() { |
| 2774 // |
| 2775 // class A {} |
| 2776 // |
| 2777 ClassElementImpl classA = ElementFactory.classElement2("A"); |
| 2778 InterfaceType typeA = classA.type; |
| 2779 expect(typeA.getMethod("m"), isNull); |
| 2780 } |
| 2781 |
| 2782 void test_getMethods() { |
| 2783 ClassElementImpl typeElement = ElementFactory.classElement2("A"); |
| 2784 MethodElementImpl methodOne = ElementFactory.methodElement("one", null); |
| 2785 MethodElementImpl methodTwo = ElementFactory.methodElement("two", null); |
| 2786 typeElement.methods = <MethodElement>[methodOne, methodTwo]; |
| 2787 InterfaceTypeImpl type = new InterfaceTypeImpl(typeElement); |
| 2788 expect(type.methods.length, 2); |
| 2789 } |
| 2790 |
| 2791 void test_getMethods_empty() { |
| 2792 ClassElementImpl typeElement = ElementFactory.classElement2("A"); |
| 2793 InterfaceTypeImpl type = new InterfaceTypeImpl(typeElement); |
| 2794 expect(type.methods.length, 0); |
| 2795 } |
| 2796 |
| 2797 void test_getMixins_nonParameterized() { |
| 2798 // |
| 2799 // class C extends Object with A, B |
| 2800 // |
| 2801 ClassElementImpl classA = ElementFactory.classElement2("A"); |
| 2802 InterfaceType typeA = classA.type; |
| 2803 ClassElementImpl classB = ElementFactory.classElement2("B"); |
| 2804 InterfaceType typeB = classB.type; |
| 2805 ClassElementImpl classC = ElementFactory.classElement2("C"); |
| 2806 classC.mixins = <InterfaceType>[typeA, typeB]; |
| 2807 List<InterfaceType> interfaces = classC.type.mixins; |
| 2808 expect(interfaces, hasLength(2)); |
| 2809 if (identical(interfaces[0], typeA)) { |
| 2810 expect(interfaces[1], same(typeB)); |
| 2811 } else { |
| 2812 expect(interfaces[0], same(typeB)); |
| 2813 expect(interfaces[1], same(typeA)); |
| 2814 } |
| 2815 } |
| 2816 |
| 2817 void test_getMixins_parameterized() { |
| 2818 // |
| 2819 // class A<E> |
| 2820 // class B<F> extends Object with A<F> |
| 2821 // |
| 2822 ClassElementImpl classA = ElementFactory.classElement2("A", ["E"]); |
| 2823 ClassElementImpl classB = ElementFactory.classElement2("B", ["F"]); |
| 2824 InterfaceType typeB = classB.type; |
| 2825 InterfaceTypeImpl typeAF = new InterfaceTypeImpl(classA); |
| 2826 typeAF.typeArguments = <DartType>[typeB.typeArguments[0]]; |
| 2827 classB.mixins = <InterfaceType>[typeAF]; |
| 2828 // |
| 2829 // B<I> |
| 2830 // |
| 2831 InterfaceType typeI = ElementFactory.classElement2("I").type; |
| 2832 InterfaceTypeImpl typeBI = new InterfaceTypeImpl(classB); |
| 2833 typeBI.typeArguments = <DartType>[typeI]; |
| 2834 List<InterfaceType> interfaces = typeBI.mixins; |
| 2835 expect(interfaces, hasLength(1)); |
| 2836 InterfaceType result = interfaces[0]; |
| 2837 expect(result.element, same(classA)); |
| 2838 expect(result.typeArguments[0], same(typeI)); |
| 2839 } |
| 2840 |
| 2841 void test_getSetter_implemented() { |
| 2842 // |
| 2843 // class A { s() {} } |
| 2844 // |
| 2845 ClassElementImpl classA = ElementFactory.classElement2("A"); |
| 2846 String setterName = "s"; |
| 2847 PropertyAccessorElement setterS = |
| 2848 ElementFactory.setterElement(setterName, false, null); |
| 2849 classA.accessors = <PropertyAccessorElement>[setterS]; |
| 2850 InterfaceType typeA = classA.type; |
| 2851 expect(typeA.getSetter(setterName), same(setterS)); |
| 2852 } |
| 2853 |
| 2854 void test_getSetter_parameterized() { |
| 2855 // |
| 2856 // class A<E> { set s(E p) {} } |
| 2857 // |
| 2858 ClassElementImpl classA = ElementFactory.classElement2("A", ["E"]); |
| 2859 DartType typeE = classA.type.typeArguments[0]; |
| 2860 String setterName = "s"; |
| 2861 PropertyAccessorElement setterS = |
| 2862 ElementFactory.setterElement(setterName, false, typeE); |
| 2863 classA.accessors = <PropertyAccessorElement>[setterS]; |
| 2864 (setterS.type as FunctionTypeImpl).typeArguments = |
| 2865 classA.type.typeArguments; |
| 2866 // |
| 2867 // A<I> |
| 2868 // |
| 2869 InterfaceType typeI = ElementFactory.classElement2("I").type; |
| 2870 InterfaceTypeImpl typeAI = new InterfaceTypeImpl(classA); |
| 2871 typeAI.typeArguments = <DartType>[typeI]; |
| 2872 PropertyAccessorElement setter = typeAI.getSetter(setterName); |
| 2873 expect(setter, isNotNull); |
| 2874 FunctionType setterType = setter.type; |
| 2875 List<DartType> parameterTypes = setterType.normalParameterTypes; |
| 2876 expect(parameterTypes, hasLength(1)); |
| 2877 expect(parameterTypes[0], same(typeI)); |
| 2878 } |
| 2879 |
| 2880 void test_getSetter_unimplemented() { |
| 2881 // |
| 2882 // class A {} |
| 2883 // |
| 2884 ClassElementImpl classA = ElementFactory.classElement2("A"); |
| 2885 InterfaceType typeA = classA.type; |
| 2886 expect(typeA.getSetter("s"), isNull); |
| 2887 } |
| 2888 |
| 2889 void test_getSuperclass_nonParameterized() { |
| 2890 // |
| 2891 // class B extends A |
| 2892 // |
| 2893 ClassElementImpl classA = ElementFactory.classElement2("A"); |
| 2894 InterfaceType typeA = classA.type; |
| 2895 ClassElementImpl classB = ElementFactory.classElement("B", typeA); |
| 2896 InterfaceType typeB = classB.type; |
| 2897 expect(typeB.superclass, same(typeA)); |
| 2898 } |
| 2899 |
| 2900 void test_getSuperclass_parameterized() { |
| 2901 // |
| 2902 // class A<E> |
| 2903 // class B<F> extends A<F> |
| 2904 // |
| 2905 ClassElementImpl classA = ElementFactory.classElement2("A", ["E"]); |
| 2906 ClassElementImpl classB = ElementFactory.classElement2("B", ["F"]); |
| 2907 InterfaceType typeB = classB.type; |
| 2908 InterfaceTypeImpl typeAF = new InterfaceTypeImpl(classA); |
| 2909 typeAF.typeArguments = <DartType>[typeB.typeArguments[0]]; |
| 2910 classB.supertype = typeAF; |
| 2911 // |
| 2912 // B<I> |
| 2913 // |
| 2914 InterfaceType typeI = ElementFactory.classElement2("I").type; |
| 2915 InterfaceTypeImpl typeBI = new InterfaceTypeImpl(classB); |
| 2916 typeBI.typeArguments = <DartType>[typeI]; |
| 2917 InterfaceType superclass = typeBI.superclass; |
| 2918 expect(superclass.element, same(classA)); |
| 2919 expect(superclass.typeArguments[0], same(typeI)); |
| 2920 } |
| 2921 |
| 2922 void test_getTypeArguments_empty() { |
| 2923 InterfaceType type = ElementFactory.classElement2("A").type; |
| 2924 expect(type.typeArguments, hasLength(0)); |
| 2925 } |
| 2926 |
| 2927 void test_hashCode() { |
| 2928 ClassElement classA = ElementFactory.classElement2("A"); |
| 2929 InterfaceType typeA = classA.type; |
| 2930 expect(0 == typeA.hashCode, isFalse); |
| 2931 } |
| 2932 |
| 2933 void test_isAssignableTo_typeVariables() { |
| 2934 // |
| 2935 // class A<E> {} |
| 2936 // class B<F, G> { |
| 2937 // A<F> af; |
| 2938 // f (A<G> ag) { |
| 2939 // af = ag; |
| 2940 // } |
| 2941 // } |
| 2942 // |
| 2943 ClassElement classA = ElementFactory.classElement2("A", ["E"]); |
| 2944 ClassElement classB = ElementFactory.classElement2("B", ["F", "G"]); |
| 2945 InterfaceTypeImpl typeAF = new InterfaceTypeImpl(classA); |
| 2946 typeAF.typeArguments = <DartType>[classB.typeParameters[0].type]; |
| 2947 InterfaceTypeImpl typeAG = new InterfaceTypeImpl(classA); |
| 2948 typeAG.typeArguments = <DartType>[classB.typeParameters[1].type]; |
| 2949 expect(typeAG.isAssignableTo(typeAF), isFalse); |
| 2950 } |
| 2951 |
| 2952 void test_isAssignableTo_void() { |
| 2953 InterfaceTypeImpl intType = _typeProvider.intType; |
| 2954 expect(VoidTypeImpl.instance.isAssignableTo(intType), isFalse); |
| 2955 } |
| 2956 |
| 2957 void test_isDirectSupertypeOf_extends() { |
| 2958 ClassElement classA = ElementFactory.classElement2("A"); |
| 2959 ClassElement classB = ElementFactory.classElement("B", classA.type); |
| 2960 InterfaceType typeA = classA.type; |
| 2961 InterfaceType typeB = classB.type; |
| 2962 expect(typeA.isDirectSupertypeOf(typeB), isTrue); |
| 2963 } |
| 2964 |
| 2965 void test_isDirectSupertypeOf_false() { |
| 2966 ClassElement classA = ElementFactory.classElement2("A"); |
| 2967 ClassElement classB = ElementFactory.classElement2("B"); |
| 2968 ClassElement classC = ElementFactory.classElement("C", classB.type); |
| 2969 InterfaceType typeA = classA.type; |
| 2970 InterfaceType typeC = classC.type; |
| 2971 expect(typeA.isDirectSupertypeOf(typeC), isFalse); |
| 2972 } |
| 2973 |
| 2974 void test_isDirectSupertypeOf_implements() { |
| 2975 ClassElementImpl classA = ElementFactory.classElement2("A"); |
| 2976 ClassElementImpl classB = ElementFactory.classElement2("B"); |
| 2977 InterfaceType typeA = classA.type; |
| 2978 InterfaceType typeB = classB.type; |
| 2979 classB.interfaces = <InterfaceType>[typeA]; |
| 2980 expect(typeA.isDirectSupertypeOf(typeB), isTrue); |
| 2981 } |
| 2982 |
| 2983 void test_isDirectSupertypeOf_with() { |
| 2984 ClassElementImpl classA = ElementFactory.classElement2("A"); |
| 2985 ClassElementImpl classB = ElementFactory.classElement2("B"); |
| 2986 InterfaceType typeA = classA.type; |
| 2987 InterfaceType typeB = classB.type; |
| 2988 classB.mixins = <InterfaceType>[typeA]; |
| 2989 expect(typeA.isDirectSupertypeOf(typeB), isTrue); |
| 2990 } |
| 2991 |
| 2992 void test_isMoreSpecificThan_bottom() { |
| 2993 DartType type = ElementFactory.classElement2("A").type; |
| 2994 expect(BottomTypeImpl.instance.isMoreSpecificThan(type), isTrue); |
| 2995 } |
| 2996 |
| 2997 void test_isMoreSpecificThan_covariance() { |
| 2998 ClassElement classA = ElementFactory.classElement2("A", ["E"]); |
| 2999 ClassElement classI = ElementFactory.classElement2("I"); |
| 3000 ClassElement classJ = ElementFactory.classElement("J", classI.type); |
| 3001 InterfaceTypeImpl typeAI = new InterfaceTypeImpl(classA); |
| 3002 InterfaceTypeImpl typeAJ = new InterfaceTypeImpl(classA); |
| 3003 typeAI.typeArguments = <DartType>[classI.type]; |
| 3004 typeAJ.typeArguments = <DartType>[classJ.type]; |
| 3005 expect(typeAJ.isMoreSpecificThan(typeAI), isTrue); |
| 3006 expect(typeAI.isMoreSpecificThan(typeAJ), isFalse); |
| 3007 } |
| 3008 |
| 3009 void test_isMoreSpecificThan_directSupertype() { |
| 3010 ClassElement classA = ElementFactory.classElement2("A"); |
| 3011 ClassElement classB = ElementFactory.classElement("B", classA.type); |
| 3012 InterfaceType typeA = classA.type; |
| 3013 InterfaceType typeB = classB.type; |
| 3014 expect(typeB.isMoreSpecificThan(typeA), isTrue); |
| 3015 // the opposite test tests a different branch in isMoreSpecificThan() |
| 3016 expect(typeA.isMoreSpecificThan(typeB), isFalse); |
| 3017 } |
| 3018 |
| 3019 void test_isMoreSpecificThan_dynamic() { |
| 3020 InterfaceType type = ElementFactory.classElement2("A").type; |
| 3021 expect(type.isMoreSpecificThan(DynamicTypeImpl.instance), isTrue); |
| 3022 } |
| 3023 |
| 3024 void test_isMoreSpecificThan_generic() { |
| 3025 ClassElement classA = ElementFactory.classElement2("A", ["E"]); |
| 3026 ClassElement classB = ElementFactory.classElement2("B"); |
| 3027 DartType dynamicType = DynamicTypeImpl.instance; |
| 3028 InterfaceType typeAOfDynamic = |
| 3029 classA.type.substitute4(<DartType>[dynamicType]); |
| 3030 InterfaceType typeAOfB = classA.type.substitute4(<DartType>[classB.type]); |
| 3031 expect(typeAOfDynamic.isMoreSpecificThan(typeAOfB), isFalse); |
| 3032 expect(typeAOfB.isMoreSpecificThan(typeAOfDynamic), isTrue); |
| 3033 } |
| 3034 |
| 3035 void test_isMoreSpecificThan_self() { |
| 3036 InterfaceType type = ElementFactory.classElement2("A").type; |
| 3037 expect(type.isMoreSpecificThan(type), isTrue); |
| 3038 } |
| 3039 |
| 3040 void test_isMoreSpecificThan_transitive_interface() { |
| 3041 // |
| 3042 // class A {} |
| 3043 // class B extends A {} |
| 3044 // class C implements B {} |
| 3045 // |
| 3046 ClassElementImpl classA = ElementFactory.classElement2("A"); |
| 3047 ClassElementImpl classB = ElementFactory.classElement("B", classA.type); |
| 3048 ClassElementImpl classC = ElementFactory.classElement2("C"); |
| 3049 classC.interfaces = <InterfaceType>[classB.type]; |
| 3050 InterfaceType typeA = classA.type; |
| 3051 InterfaceType typeC = classC.type; |
| 3052 expect(typeC.isMoreSpecificThan(typeA), isTrue); |
| 3053 } |
| 3054 |
| 3055 void test_isMoreSpecificThan_transitive_mixin() { |
| 3056 // |
| 3057 // class A {} |
| 3058 // class B extends A {} |
| 3059 // class C with B {} |
| 3060 // |
| 3061 ClassElementImpl classA = ElementFactory.classElement2("A"); |
| 3062 ClassElementImpl classB = ElementFactory.classElement("B", classA.type); |
| 3063 ClassElementImpl classC = ElementFactory.classElement2("C"); |
| 3064 classC.mixins = <InterfaceType>[classB.type]; |
| 3065 InterfaceType typeA = classA.type; |
| 3066 InterfaceType typeC = classC.type; |
| 3067 expect(typeC.isMoreSpecificThan(typeA), isTrue); |
| 3068 } |
| 3069 |
| 3070 void test_isMoreSpecificThan_transitive_recursive() { |
| 3071 // |
| 3072 // class A extends B {} |
| 3073 // class B extends A {} |
| 3074 // class C {} |
| 3075 // |
| 3076 ClassElementImpl classA = ElementFactory.classElement2("A"); |
| 3077 ClassElementImpl classB = ElementFactory.classElement("B", classA.type); |
| 3078 ClassElementImpl classC = ElementFactory.classElement2("C"); |
| 3079 InterfaceType typeA = classA.type; |
| 3080 InterfaceType typeC = classC.type; |
| 3081 classA.supertype = classB.type; |
| 3082 expect(typeA.isMoreSpecificThan(typeC), isFalse); |
| 3083 } |
| 3084 |
| 3085 void test_isMoreSpecificThan_transitive_superclass() { |
| 3086 // |
| 3087 // class A {} |
| 3088 // class B extends A {} |
| 3089 // class C extends B {} |
| 3090 // |
| 3091 ClassElement classA = ElementFactory.classElement2("A"); |
| 3092 ClassElement classB = ElementFactory.classElement("B", classA.type); |
| 3093 ClassElement classC = ElementFactory.classElement("C", classB.type); |
| 3094 InterfaceType typeA = classA.type; |
| 3095 InterfaceType typeC = classC.type; |
| 3096 expect(typeC.isMoreSpecificThan(typeA), isTrue); |
| 3097 } |
| 3098 |
| 3099 void test_isMoreSpecificThan_typeParameterType() { |
| 3100 // |
| 3101 // class A<E> {} |
| 3102 // |
| 3103 ClassElement classA = ElementFactory.classElement2("A", ["E"]); |
| 3104 InterfaceType typeA = classA.type; |
| 3105 TypeParameterType parameterType = classA.typeParameters[0].type; |
| 3106 DartType objectType = _typeProvider.objectType; |
| 3107 expect(parameterType.isMoreSpecificThan(objectType), isTrue); |
| 3108 expect(parameterType.isMoreSpecificThan(typeA), isFalse); |
| 3109 } |
| 3110 |
| 3111 void test_isMoreSpecificThan_typeParameterType_withBound() { |
| 3112 // |
| 3113 // class A {} |
| 3114 // class B<E extends A> {} |
| 3115 // |
| 3116 ClassElement classA = ElementFactory.classElement2("A"); |
| 3117 InterfaceType typeA = classA.type; |
| 3118 ClassElementImpl classB = ElementFactory.classElement2("B"); |
| 3119 TypeParameterElementImpl parameterEA = |
| 3120 new TypeParameterElementImpl.forNode(AstFactory.identifier3("E")); |
| 3121 TypeParameterType parameterAEType = new TypeParameterTypeImpl(parameterEA); |
| 3122 parameterEA.bound = typeA; |
| 3123 parameterEA.type = parameterAEType; |
| 3124 classB.typeParameters = <TypeParameterElementImpl>[parameterEA]; |
| 3125 expect(parameterAEType.isMoreSpecificThan(typeA), isTrue); |
| 3126 } |
| 3127 |
| 3128 void test_isSubtypeOf_directSubtype() { |
| 3129 ClassElement classA = ElementFactory.classElement2("A"); |
| 3130 ClassElement classB = ElementFactory.classElement("B", classA.type); |
| 3131 InterfaceType typeA = classA.type; |
| 3132 InterfaceType typeB = classB.type; |
| 3133 expect(typeB.isSubtypeOf(typeA), isTrue); |
| 3134 expect(typeA.isSubtypeOf(typeB), isFalse); |
| 3135 } |
| 3136 |
| 3137 void test_isSubtypeOf_dynamic() { |
| 3138 ClassElement classA = ElementFactory.classElement2("A"); |
| 3139 InterfaceType typeA = classA.type; |
| 3140 DartType dynamicType = DynamicTypeImpl.instance; |
| 3141 expect(dynamicType.isSubtypeOf(typeA), isTrue); |
| 3142 expect(typeA.isSubtypeOf(dynamicType), isTrue); |
| 3143 } |
| 3144 |
| 3145 void test_isSubtypeOf_function() { |
| 3146 // |
| 3147 // void f(String s) {} |
| 3148 // class A { |
| 3149 // void call(String s) {} |
| 3150 // } |
| 3151 // |
| 3152 InterfaceType stringType = _typeProvider.stringType; |
| 3153 ClassElementImpl classA = ElementFactory.classElement2("A"); |
| 3154 classA.methods = <MethodElement>[ |
| 3155 ElementFactory.methodElement("call", VoidTypeImpl.instance, [stringType]) |
| 3156 ]; |
| 3157 FunctionType functionType = ElementFactory |
| 3158 .functionElement5("f", <ClassElement>[stringType.element]).type; |
| 3159 expect(classA.type.isSubtypeOf(functionType), isTrue); |
| 3160 } |
| 3161 |
| 3162 void test_isSubtypeOf_generic() { |
| 3163 ClassElement classA = ElementFactory.classElement2("A", ["E"]); |
| 3164 ClassElement classB = ElementFactory.classElement2("B"); |
| 3165 DartType dynamicType = DynamicTypeImpl.instance; |
| 3166 InterfaceType typeAOfDynamic = |
| 3167 classA.type.substitute4(<DartType>[dynamicType]); |
| 3168 InterfaceType typeAOfB = classA.type.substitute4(<DartType>[classB.type]); |
| 3169 expect(typeAOfDynamic.isSubtypeOf(typeAOfB), isTrue); |
| 3170 expect(typeAOfB.isSubtypeOf(typeAOfDynamic), isTrue); |
| 3171 } |
| 3172 |
| 3173 void test_isSubtypeOf_interface() { |
| 3174 ClassElement classA = ElementFactory.classElement2("A"); |
| 3175 ClassElement classB = ElementFactory.classElement("B", classA.type); |
| 3176 ClassElementImpl classC = ElementFactory.classElement2("C"); |
| 3177 InterfaceType typeObject = classA.supertype; |
| 3178 InterfaceType typeA = classA.type; |
| 3179 InterfaceType typeB = classB.type; |
| 3180 InterfaceType typeC = classC.type; |
| 3181 classC.interfaces = <InterfaceType>[typeB]; |
| 3182 expect(typeC.isSubtypeOf(typeB), isTrue); |
| 3183 expect(typeC.isSubtypeOf(typeObject), isTrue); |
| 3184 expect(typeC.isSubtypeOf(typeA), isTrue); |
| 3185 expect(typeA.isSubtypeOf(typeC), isFalse); |
| 3186 } |
| 3187 |
| 3188 void test_isSubtypeOf_mixins() { |
| 3189 // |
| 3190 // class A {} |
| 3191 // class B extends A {} |
| 3192 // class C with B {} |
| 3193 // |
| 3194 ClassElement classA = ElementFactory.classElement2("A"); |
| 3195 ClassElement classB = ElementFactory.classElement("B", classA.type); |
| 3196 ClassElementImpl classC = ElementFactory.classElement2("C"); |
| 3197 InterfaceType typeObject = classA.supertype; |
| 3198 InterfaceType typeA = classA.type; |
| 3199 InterfaceType typeB = classB.type; |
| 3200 InterfaceType typeC = classC.type; |
| 3201 classC.mixins = <InterfaceType>[typeB]; |
| 3202 expect(typeC.isSubtypeOf(typeB), isTrue); |
| 3203 expect(typeC.isSubtypeOf(typeObject), isTrue); |
| 3204 expect(typeC.isSubtypeOf(typeA), isTrue); |
| 3205 expect(typeA.isSubtypeOf(typeC), isFalse); |
| 3206 } |
| 3207 |
| 3208 void test_isSubtypeOf_object() { |
| 3209 ClassElement classA = ElementFactory.classElement2("A"); |
| 3210 InterfaceType typeA = classA.type; |
| 3211 InterfaceType typeObject = classA.supertype; |
| 3212 expect(typeA.isSubtypeOf(typeObject), isTrue); |
| 3213 expect(typeObject.isSubtypeOf(typeA), isFalse); |
| 3214 } |
| 3215 |
| 3216 void test_isSubtypeOf_self() { |
| 3217 ClassElement classA = ElementFactory.classElement2("A"); |
| 3218 InterfaceType typeA = classA.type; |
| 3219 expect(typeA.isSubtypeOf(typeA), isTrue); |
| 3220 } |
| 3221 |
| 3222 void test_isSubtypeOf_transitive_recursive() { |
| 3223 // |
| 3224 // class A extends B {} |
| 3225 // class B extends A {} |
| 3226 // class C {} |
| 3227 // |
| 3228 ClassElementImpl classA = ElementFactory.classElement2("A"); |
| 3229 ClassElementImpl classB = ElementFactory.classElement("B", classA.type); |
| 3230 ClassElementImpl classC = ElementFactory.classElement2("C"); |
| 3231 InterfaceType typeA = classA.type; |
| 3232 InterfaceType typeC = classC.type; |
| 3233 classA.supertype = classB.type; |
| 3234 expect(typeA.isSubtypeOf(typeC), isFalse); |
| 3235 } |
| 3236 |
| 3237 void test_isSubtypeOf_transitive_superclass() { |
| 3238 ClassElement classA = ElementFactory.classElement2("A"); |
| 3239 ClassElement classB = ElementFactory.classElement("B", classA.type); |
| 3240 ClassElement classC = ElementFactory.classElement("C", classB.type); |
| 3241 InterfaceType typeA = classA.type; |
| 3242 InterfaceType typeC = classC.type; |
| 3243 expect(typeC.isSubtypeOf(typeA), isTrue); |
| 3244 expect(typeA.isSubtypeOf(typeC), isFalse); |
| 3245 } |
| 3246 |
| 3247 void test_isSubtypeOf_typeArguments() { |
| 3248 DartType dynamicType = DynamicTypeImpl.instance; |
| 3249 ClassElement classA = ElementFactory.classElement2("A", ["E"]); |
| 3250 ClassElement classI = ElementFactory.classElement2("I"); |
| 3251 ClassElement classJ = ElementFactory.classElement("J", classI.type); |
| 3252 ClassElement classK = ElementFactory.classElement2("K"); |
| 3253 InterfaceType typeA = classA.type; |
| 3254 InterfaceType typeA_dynamic = typeA.substitute4(<DartType>[dynamicType]); |
| 3255 InterfaceTypeImpl typeAI = new InterfaceTypeImpl(classA); |
| 3256 InterfaceTypeImpl typeAJ = new InterfaceTypeImpl(classA); |
| 3257 InterfaceTypeImpl typeAK = new InterfaceTypeImpl(classA); |
| 3258 typeAI.typeArguments = <DartType>[classI.type]; |
| 3259 typeAJ.typeArguments = <DartType>[classJ.type]; |
| 3260 typeAK.typeArguments = <DartType>[classK.type]; |
| 3261 // A<J> <: A<I> since J <: I |
| 3262 expect(typeAJ.isSubtypeOf(typeAI), isTrue); |
| 3263 expect(typeAI.isSubtypeOf(typeAJ), isFalse); |
| 3264 // A<I> <: A<I> since I <: I |
| 3265 expect(typeAI.isSubtypeOf(typeAI), isTrue); |
| 3266 // A <: A<I> and A <: A<J> |
| 3267 expect(typeA_dynamic.isSubtypeOf(typeAI), isTrue); |
| 3268 expect(typeA_dynamic.isSubtypeOf(typeAJ), isTrue); |
| 3269 // A<I> <: A and A<J> <: A |
| 3270 expect(typeAI.isSubtypeOf(typeA_dynamic), isTrue); |
| 3271 expect(typeAJ.isSubtypeOf(typeA_dynamic), isTrue); |
| 3272 // A<I> !<: A<K> and A<K> !<: A<I> |
| 3273 expect(typeAI.isSubtypeOf(typeAK), isFalse); |
| 3274 expect(typeAK.isSubtypeOf(typeAI), isFalse); |
| 3275 } |
| 3276 |
| 3277 void test_isSubtypeOf_typeParameter() { |
| 3278 // |
| 3279 // class A<E> {} |
| 3280 // |
| 3281 ClassElement classA = ElementFactory.classElement2("A", ["E"]); |
| 3282 InterfaceType typeA = classA.type; |
| 3283 TypeParameterType parameterType = classA.typeParameters[0].type; |
| 3284 expect(typeA.isSubtypeOf(parameterType), isFalse); |
| 3285 } |
| 3286 |
| 3287 void test_isSupertypeOf_directSupertype() { |
| 3288 ClassElement classA = ElementFactory.classElement2("A"); |
| 3289 ClassElement classB = ElementFactory.classElement("B", classA.type); |
| 3290 InterfaceType typeA = classA.type; |
| 3291 InterfaceType typeB = classB.type; |
| 3292 expect(typeB.isSupertypeOf(typeA), isFalse); |
| 3293 expect(typeA.isSupertypeOf(typeB), isTrue); |
| 3294 } |
| 3295 |
| 3296 void test_isSupertypeOf_dynamic() { |
| 3297 ClassElement classA = ElementFactory.classElement2("A"); |
| 3298 InterfaceType typeA = classA.type; |
| 3299 DartType dynamicType = DynamicTypeImpl.instance; |
| 3300 expect(dynamicType.isSupertypeOf(typeA), isTrue); |
| 3301 expect(typeA.isSupertypeOf(dynamicType), isTrue); |
| 3302 } |
| 3303 |
| 3304 void test_isSupertypeOf_indirectSupertype() { |
| 3305 ClassElement classA = ElementFactory.classElement2("A"); |
| 3306 ClassElement classB = ElementFactory.classElement("B", classA.type); |
| 3307 ClassElement classC = ElementFactory.classElement("C", classB.type); |
| 3308 InterfaceType typeA = classA.type; |
| 3309 InterfaceType typeC = classC.type; |
| 3310 expect(typeC.isSupertypeOf(typeA), isFalse); |
| 3311 expect(typeA.isSupertypeOf(typeC), isTrue); |
| 3312 } |
| 3313 |
| 3314 void test_isSupertypeOf_interface() { |
| 3315 ClassElement classA = ElementFactory.classElement2("A"); |
| 3316 ClassElement classB = ElementFactory.classElement("B", classA.type); |
| 3317 ClassElementImpl classC = ElementFactory.classElement2("C"); |
| 3318 InterfaceType typeObject = classA.supertype; |
| 3319 InterfaceType typeA = classA.type; |
| 3320 InterfaceType typeB = classB.type; |
| 3321 InterfaceType typeC = classC.type; |
| 3322 classC.interfaces = <InterfaceType>[typeB]; |
| 3323 expect(typeB.isSupertypeOf(typeC), isTrue); |
| 3324 expect(typeObject.isSupertypeOf(typeC), isTrue); |
| 3325 expect(typeA.isSupertypeOf(typeC), isTrue); |
| 3326 expect(typeC.isSupertypeOf(typeA), isFalse); |
| 3327 } |
| 3328 |
| 3329 void test_isSupertypeOf_mixins() { |
| 3330 // |
| 3331 // class A {} |
| 3332 // class B extends A {} |
| 3333 // class C with B {} |
| 3334 // |
| 3335 ClassElement classA = ElementFactory.classElement2("A"); |
| 3336 ClassElement classB = ElementFactory.classElement("B", classA.type); |
| 3337 ClassElementImpl classC = ElementFactory.classElement2("C"); |
| 3338 InterfaceType typeObject = classA.supertype; |
| 3339 InterfaceType typeA = classA.type; |
| 3340 InterfaceType typeB = classB.type; |
| 3341 InterfaceType typeC = classC.type; |
| 3342 classC.mixins = <InterfaceType>[typeB]; |
| 3343 expect(typeB.isSupertypeOf(typeC), isTrue); |
| 3344 expect(typeObject.isSupertypeOf(typeC), isTrue); |
| 3345 expect(typeA.isSupertypeOf(typeC), isTrue); |
| 3346 expect(typeC.isSupertypeOf(typeA), isFalse); |
| 3347 } |
| 3348 |
| 3349 void test_isSupertypeOf_object() { |
| 3350 ClassElement classA = ElementFactory.classElement2("A"); |
| 3351 InterfaceType typeA = classA.type; |
| 3352 InterfaceType typeObject = classA.supertype; |
| 3353 expect(typeA.isSupertypeOf(typeObject), isFalse); |
| 3354 expect(typeObject.isSupertypeOf(typeA), isTrue); |
| 3355 } |
| 3356 |
| 3357 void test_isSupertypeOf_self() { |
| 3358 ClassElement classA = ElementFactory.classElement2("A"); |
| 3359 InterfaceType typeA = classA.type; |
| 3360 expect(typeA.isSupertypeOf(typeA), isTrue); |
| 3361 } |
| 3362 |
| 3363 void test_lookUpGetter_implemented() { |
| 3364 // |
| 3365 // class A { g {} } |
| 3366 // |
| 3367 ClassElementImpl classA = ElementFactory.classElement2("A"); |
| 3368 String getterName = "g"; |
| 3369 PropertyAccessorElement getterG = |
| 3370 ElementFactory.getterElement(getterName, false, null); |
| 3371 classA.accessors = <PropertyAccessorElement>[getterG]; |
| 3372 InterfaceType typeA = classA.type; |
| 3373 LibraryElementImpl library = |
| 3374 ElementFactory.library(createAnalysisContext(), "lib"); |
| 3375 CompilationUnitElement unit = library.definingCompilationUnit; |
| 3376 (unit as CompilationUnitElementImpl).types = <ClassElement>[classA]; |
| 3377 expect(typeA.lookUpGetter(getterName, library), same(getterG)); |
| 3378 } |
| 3379 |
| 3380 void test_lookUpGetter_inherited() { |
| 3381 // |
| 3382 // class A { g {} } |
| 3383 // class B extends A {} |
| 3384 // |
| 3385 ClassElementImpl classA = ElementFactory.classElement2("A"); |
| 3386 String getterName = "g"; |
| 3387 PropertyAccessorElement getterG = |
| 3388 ElementFactory.getterElement(getterName, false, null); |
| 3389 classA.accessors = <PropertyAccessorElement>[getterG]; |
| 3390 ClassElementImpl classB = ElementFactory.classElement("B", classA.type); |
| 3391 InterfaceType typeB = classB.type; |
| 3392 LibraryElementImpl library = |
| 3393 ElementFactory.library(createAnalysisContext(), "lib"); |
| 3394 CompilationUnitElement unit = library.definingCompilationUnit; |
| 3395 (unit as CompilationUnitElementImpl).types = <ClassElement>[classA, classB]; |
| 3396 expect(typeB.lookUpGetter(getterName, library), same(getterG)); |
| 3397 } |
| 3398 |
| 3399 void test_lookUpGetter_mixin_shadowing() { |
| 3400 // |
| 3401 // class B {} |
| 3402 // class M1 { get g {} } |
| 3403 // class M2 { get g {} } |
| 3404 // class C extends B with M1, M2 {} |
| 3405 // |
| 3406 TestTypeProvider typeProvider = new TestTypeProvider(); |
| 3407 String getterName = 'g'; |
| 3408 ClassElementImpl classB = ElementFactory.classElement2('B'); |
| 3409 ClassElementImpl classM1 = ElementFactory.classElement2('M1'); |
| 3410 PropertyAccessorElementImpl getterM1g = ElementFactory.getterElement( |
| 3411 getterName, false, typeProvider.dynamicType); |
| 3412 classM1.accessors = <PropertyAccessorElement>[getterM1g]; |
| 3413 ClassElementImpl classM2 = ElementFactory.classElement2('M2'); |
| 3414 PropertyAccessorElementImpl getterM2g = ElementFactory.getterElement( |
| 3415 getterName, false, typeProvider.dynamicType); |
| 3416 classM2.accessors = <PropertyAccessorElement>[getterM2g]; |
| 3417 ClassElementImpl classC = ElementFactory.classElement('C', classB.type); |
| 3418 classC.mixins = <InterfaceType>[classM1.type, classM2.type]; |
| 3419 LibraryElementImpl library = |
| 3420 ElementFactory.library(createAnalysisContext(), "lib"); |
| 3421 CompilationUnitElementImpl unit = library.definingCompilationUnit; |
| 3422 unit.types = <ClassElement>[classB, classM1, classM2, classC]; |
| 3423 expect(classC.type.lookUpGetter(getterName, library), getterM2g); |
| 3424 } |
| 3425 |
| 3426 void test_lookUpGetter_recursive() { |
| 3427 // |
| 3428 // class A extends B {} |
| 3429 // class B extends A {} |
| 3430 // |
| 3431 ClassElementImpl classA = ElementFactory.classElement2("A"); |
| 3432 InterfaceType typeA = classA.type; |
| 3433 ClassElementImpl classB = ElementFactory.classElement("B", typeA); |
| 3434 classA.supertype = classB.type; |
| 3435 LibraryElementImpl library = |
| 3436 ElementFactory.library(createAnalysisContext(), "lib"); |
| 3437 CompilationUnitElement unit = library.definingCompilationUnit; |
| 3438 (unit as CompilationUnitElementImpl).types = <ClassElement>[classA, classB]; |
| 3439 expect(typeA.lookUpGetter("g", library), isNull); |
| 3440 } |
| 3441 |
| 3442 void test_lookUpGetter_unimplemented() { |
| 3443 // |
| 3444 // class A {} |
| 3445 // |
| 3446 ClassElementImpl classA = ElementFactory.classElement2("A"); |
| 3447 InterfaceType typeA = classA.type; |
| 3448 LibraryElementImpl library = |
| 3449 ElementFactory.library(createAnalysisContext(), "lib"); |
| 3450 CompilationUnitElement unit = library.definingCompilationUnit; |
| 3451 (unit as CompilationUnitElementImpl).types = <ClassElement>[classA]; |
| 3452 expect(typeA.lookUpGetter("g", library), isNull); |
| 3453 } |
| 3454 |
| 3455 void test_lookUpMethod_implemented() { |
| 3456 // |
| 3457 // class A { m() {} } |
| 3458 // |
| 3459 ClassElementImpl classA = ElementFactory.classElement2("A"); |
| 3460 String methodName = "m"; |
| 3461 MethodElementImpl methodM = ElementFactory.methodElement(methodName, null); |
| 3462 classA.methods = <MethodElement>[methodM]; |
| 3463 InterfaceType typeA = classA.type; |
| 3464 LibraryElementImpl library = |
| 3465 ElementFactory.library(createAnalysisContext(), "lib"); |
| 3466 CompilationUnitElement unit = library.definingCompilationUnit; |
| 3467 (unit as CompilationUnitElementImpl).types = <ClassElement>[classA]; |
| 3468 expect(typeA.lookUpMethod(methodName, library), same(methodM)); |
| 3469 } |
| 3470 |
| 3471 void test_lookUpMethod_inherited() { |
| 3472 // |
| 3473 // class A { m() {} } |
| 3474 // class B extends A {} |
| 3475 // |
| 3476 ClassElementImpl classA = ElementFactory.classElement2("A"); |
| 3477 String methodName = "m"; |
| 3478 MethodElementImpl methodM = ElementFactory.methodElement(methodName, null); |
| 3479 classA.methods = <MethodElement>[methodM]; |
| 3480 ClassElementImpl classB = ElementFactory.classElement("B", classA.type); |
| 3481 InterfaceType typeB = classB.type; |
| 3482 LibraryElementImpl library = |
| 3483 ElementFactory.library(createAnalysisContext(), "lib"); |
| 3484 CompilationUnitElement unit = library.definingCompilationUnit; |
| 3485 (unit as CompilationUnitElementImpl).types = <ClassElement>[classA, classB]; |
| 3486 expect(typeB.lookUpMethod(methodName, library), same(methodM)); |
| 3487 } |
| 3488 |
| 3489 void test_lookUpMethod_mixin_shadowing() { |
| 3490 // |
| 3491 // class B {} |
| 3492 // class M1 { m() {} } |
| 3493 // class M2 { m() {} } |
| 3494 // class C extends B with M1, M2 {} |
| 3495 // |
| 3496 String methodName = 'm'; |
| 3497 ClassElementImpl classB = ElementFactory.classElement2('B'); |
| 3498 ClassElementImpl classM1 = ElementFactory.classElement2('M1'); |
| 3499 MethodElementImpl methodM1m = |
| 3500 ElementFactory.methodElement(methodName, null); |
| 3501 classM1.methods = <MethodElement>[methodM1m]; |
| 3502 ClassElementImpl classM2 = ElementFactory.classElement2('M2'); |
| 3503 MethodElementImpl methodM2m = |
| 3504 ElementFactory.methodElement(methodName, null); |
| 3505 classM2.methods = <MethodElement>[methodM2m]; |
| 3506 ClassElementImpl classC = ElementFactory.classElement('C', classB.type); |
| 3507 classC.mixins = <InterfaceType>[classM1.type, classM2.type]; |
| 3508 LibraryElementImpl library = |
| 3509 ElementFactory.library(createAnalysisContext(), "lib"); |
| 3510 CompilationUnitElementImpl unit = library.definingCompilationUnit; |
| 3511 unit.types = <ClassElement>[classB, classM1, classM2, classC]; |
| 3512 expect(classC.type.lookUpMethod(methodName, library), methodM2m); |
| 3513 } |
| 3514 |
| 3515 void test_lookUpMethod_parameterized() { |
| 3516 // |
| 3517 // class A<E> { E m(E p) {} } |
| 3518 // class B<F> extends A<F> {} |
| 3519 // |
| 3520 ClassElementImpl classA = ElementFactory.classElement2("A", ["E"]); |
| 3521 DartType typeE = classA.type.typeArguments[0]; |
| 3522 String methodName = "m"; |
| 3523 MethodElementImpl methodM = |
| 3524 ElementFactory.methodElement(methodName, typeE, [typeE]); |
| 3525 classA.methods = <MethodElement>[methodM]; |
| 3526 (methodM.type as FunctionTypeImpl).typeArguments = |
| 3527 classA.type.typeArguments; |
| 3528 ClassElementImpl classB = ElementFactory.classElement2("B", ["F"]); |
| 3529 InterfaceType typeB = classB.type; |
| 3530 InterfaceTypeImpl typeAF = new InterfaceTypeImpl(classA); |
| 3531 typeAF.typeArguments = <DartType>[typeB.typeArguments[0]]; |
| 3532 classB.supertype = typeAF; |
| 3533 LibraryElementImpl library = |
| 3534 ElementFactory.library(createAnalysisContext(), "lib"); |
| 3535 CompilationUnitElement unit = library.definingCompilationUnit; |
| 3536 (unit as CompilationUnitElementImpl).types = <ClassElement>[classA]; |
| 3537 // |
| 3538 // B<I> |
| 3539 // |
| 3540 InterfaceType typeI = ElementFactory.classElement2("I").type; |
| 3541 InterfaceTypeImpl typeBI = new InterfaceTypeImpl(classB); |
| 3542 typeBI.typeArguments = <DartType>[typeI]; |
| 3543 MethodElement method = typeBI.lookUpMethod(methodName, library); |
| 3544 expect(method, isNotNull); |
| 3545 FunctionType methodType = method.type; |
| 3546 expect(methodType.returnType, same(typeI)); |
| 3547 List<DartType> parameterTypes = methodType.normalParameterTypes; |
| 3548 expect(parameterTypes, hasLength(1)); |
| 3549 expect(parameterTypes[0], same(typeI)); |
| 3550 } |
| 3551 |
| 3552 void test_lookUpMethod_recursive() { |
| 3553 // |
| 3554 // class A extends B {} |
| 3555 // class B extends A {} |
| 3556 // |
| 3557 ClassElementImpl classA = ElementFactory.classElement2("A"); |
| 3558 InterfaceType typeA = classA.type; |
| 3559 ClassElementImpl classB = ElementFactory.classElement("B", typeA); |
| 3560 classA.supertype = classB.type; |
| 3561 LibraryElementImpl library = |
| 3562 ElementFactory.library(createAnalysisContext(), "lib"); |
| 3563 CompilationUnitElement unit = library.definingCompilationUnit; |
| 3564 (unit as CompilationUnitElementImpl).types = <ClassElement>[classA, classB]; |
| 3565 expect(typeA.lookUpMethod("m", library), isNull); |
| 3566 } |
| 3567 |
| 3568 void test_lookUpMethod_unimplemented() { |
| 3569 // |
| 3570 // class A {} |
| 3571 // |
| 3572 ClassElementImpl classA = ElementFactory.classElement2("A"); |
| 3573 InterfaceType typeA = classA.type; |
| 3574 LibraryElementImpl library = |
| 3575 ElementFactory.library(createAnalysisContext(), "lib"); |
| 3576 CompilationUnitElement unit = library.definingCompilationUnit; |
| 3577 (unit as CompilationUnitElementImpl).types = <ClassElement>[classA]; |
| 3578 expect(typeA.lookUpMethod("m", library), isNull); |
| 3579 } |
| 3580 |
| 3581 void test_lookUpSetter_implemented() { |
| 3582 // |
| 3583 // class A { s(x) {} } |
| 3584 // |
| 3585 ClassElementImpl classA = ElementFactory.classElement2("A"); |
| 3586 String setterName = "s"; |
| 3587 PropertyAccessorElement setterS = |
| 3588 ElementFactory.setterElement(setterName, false, null); |
| 3589 classA.accessors = <PropertyAccessorElement>[setterS]; |
| 3590 InterfaceType typeA = classA.type; |
| 3591 LibraryElementImpl library = |
| 3592 ElementFactory.library(createAnalysisContext(), "lib"); |
| 3593 CompilationUnitElement unit = library.definingCompilationUnit; |
| 3594 (unit as CompilationUnitElementImpl).types = <ClassElement>[classA]; |
| 3595 expect(typeA.lookUpSetter(setterName, library), same(setterS)); |
| 3596 } |
| 3597 |
| 3598 void test_lookUpSetter_inherited() { |
| 3599 // |
| 3600 // class A { s(x) {} } |
| 3601 // class B extends A {} |
| 3602 // |
| 3603 ClassElementImpl classA = ElementFactory.classElement2("A"); |
| 3604 String setterName = "g"; |
| 3605 PropertyAccessorElement setterS = |
| 3606 ElementFactory.setterElement(setterName, false, null); |
| 3607 classA.accessors = <PropertyAccessorElement>[setterS]; |
| 3608 ClassElementImpl classB = ElementFactory.classElement("B", classA.type); |
| 3609 InterfaceType typeB = classB.type; |
| 3610 LibraryElementImpl library = |
| 3611 ElementFactory.library(createAnalysisContext(), "lib"); |
| 3612 CompilationUnitElement unit = library.definingCompilationUnit; |
| 3613 (unit as CompilationUnitElementImpl).types = <ClassElement>[classA, classB]; |
| 3614 expect(typeB.lookUpSetter(setterName, library), same(setterS)); |
| 3615 } |
| 3616 |
| 3617 void test_lookUpSetter_mixin_shadowing() { |
| 3618 // |
| 3619 // class B {} |
| 3620 // class M1 { set s() {} } |
| 3621 // class M2 { set s() {} } |
| 3622 // class C extends B with M1, M2 {} |
| 3623 // |
| 3624 TestTypeProvider typeProvider = new TestTypeProvider(); |
| 3625 String setterName = 's'; |
| 3626 ClassElementImpl classB = ElementFactory.classElement2('B'); |
| 3627 ClassElementImpl classM1 = ElementFactory.classElement2('M1'); |
| 3628 PropertyAccessorElementImpl setterM1g = ElementFactory.setterElement( |
| 3629 setterName, false, typeProvider.dynamicType); |
| 3630 classM1.accessors = <PropertyAccessorElement>[setterM1g]; |
| 3631 ClassElementImpl classM2 = ElementFactory.classElement2('M2'); |
| 3632 PropertyAccessorElementImpl setterM2g = ElementFactory.getterElement( |
| 3633 setterName, false, typeProvider.dynamicType); |
| 3634 classM2.accessors = <PropertyAccessorElement>[setterM2g]; |
| 3635 ClassElementImpl classC = ElementFactory.classElement('C', classB.type); |
| 3636 classC.mixins = <InterfaceType>[classM1.type, classM2.type]; |
| 3637 LibraryElementImpl library = |
| 3638 ElementFactory.library(createAnalysisContext(), "lib"); |
| 3639 CompilationUnitElementImpl unit = library.definingCompilationUnit; |
| 3640 unit.types = <ClassElement>[classB, classM1, classM2, classC]; |
| 3641 expect(classC.type.lookUpGetter(setterName, library), setterM2g); |
| 3642 } |
| 3643 |
| 3644 void test_lookUpSetter_recursive() { |
| 3645 // |
| 3646 // class A extends B {} |
| 3647 // class B extends A {} |
| 3648 // |
| 3649 ClassElementImpl classA = ElementFactory.classElement2("A"); |
| 3650 InterfaceType typeA = classA.type; |
| 3651 ClassElementImpl classB = ElementFactory.classElement("B", typeA); |
| 3652 classA.supertype = classB.type; |
| 3653 LibraryElementImpl library = |
| 3654 ElementFactory.library(createAnalysisContext(), "lib"); |
| 3655 CompilationUnitElement unit = library.definingCompilationUnit; |
| 3656 (unit as CompilationUnitElementImpl).types = <ClassElement>[classA, classB]; |
| 3657 expect(typeA.lookUpSetter("s", library), isNull); |
| 3658 } |
| 3659 |
| 3660 void test_lookUpSetter_unimplemented() { |
| 3661 // |
| 3662 // class A {} |
| 3663 // |
| 3664 ClassElementImpl classA = ElementFactory.classElement2("A"); |
| 3665 InterfaceType typeA = classA.type; |
| 3666 LibraryElementImpl library = |
| 3667 ElementFactory.library(createAnalysisContext(), "lib"); |
| 3668 CompilationUnitElement unit = library.definingCompilationUnit; |
| 3669 (unit as CompilationUnitElementImpl).types = <ClassElement>[classA]; |
| 3670 expect(typeA.lookUpSetter("s", library), isNull); |
| 3671 } |
| 3672 |
| 3673 void test_setTypeArguments() { |
| 3674 InterfaceTypeImpl type = |
| 3675 ElementFactory.classElement2("A").type as InterfaceTypeImpl; |
| 3676 List<DartType> typeArguments = <DartType>[ |
| 3677 ElementFactory.classElement2("B").type, |
| 3678 ElementFactory.classElement2("C").type |
| 3679 ]; |
| 3680 type.typeArguments = typeArguments; |
| 3681 expect(type.typeArguments, typeArguments); |
| 3682 } |
| 3683 |
| 3684 void test_substitute_equal() { |
| 3685 ClassElement classAE = ElementFactory.classElement2("A", ["E"]); |
| 3686 InterfaceType typeAE = classAE.type; |
| 3687 InterfaceType argumentType = ElementFactory.classElement2("B").type; |
| 3688 List<DartType> args = [argumentType]; |
| 3689 List<DartType> params = [classAE.typeParameters[0].type]; |
| 3690 InterfaceType typeAESubbed = typeAE.substitute2(args, params); |
| 3691 expect(typeAESubbed.element, classAE); |
| 3692 List<DartType> resultArguments = typeAESubbed.typeArguments; |
| 3693 expect(resultArguments, hasLength(1)); |
| 3694 expect(resultArguments[0], argumentType); |
| 3695 } |
| 3696 |
| 3697 void test_substitute_exception() { |
| 3698 try { |
| 3699 ClassElementImpl classA = ElementFactory.classElement2("A"); |
| 3700 InterfaceTypeImpl type = new InterfaceTypeImpl(classA); |
| 3701 InterfaceType argumentType = ElementFactory.classElement2("B").type; |
| 3702 type.substitute2(<DartType>[argumentType], <DartType>[]); |
| 3703 fail( |
| 3704 "Expected to encounter exception, argument and parameter type array le
ngths not equal."); |
| 3705 } catch (e) { |
| 3706 // Expected result |
| 3707 } |
| 3708 } |
| 3709 |
| 3710 void test_substitute_notEqual() { |
| 3711 // The [test_substitute_equals] above has a slightly higher level |
| 3712 // implementation. |
| 3713 ClassElementImpl classA = ElementFactory.classElement2("A"); |
| 3714 TypeParameterElementImpl parameterElement = |
| 3715 new TypeParameterElementImpl.forNode(AstFactory.identifier3("E")); |
| 3716 InterfaceTypeImpl type = new InterfaceTypeImpl(classA); |
| 3717 TypeParameterTypeImpl parameter = |
| 3718 new TypeParameterTypeImpl(parameterElement); |
| 3719 type.typeArguments = <DartType>[parameter]; |
| 3720 InterfaceType argumentType = ElementFactory.classElement2("B").type; |
| 3721 TypeParameterTypeImpl parameterType = new TypeParameterTypeImpl( |
| 3722 new TypeParameterElementImpl.forNode(AstFactory.identifier3("F"))); |
| 3723 InterfaceType result = |
| 3724 type.substitute2(<DartType>[argumentType], <DartType>[parameterType]); |
| 3725 expect(result.element, classA); |
| 3726 List<DartType> resultArguments = result.typeArguments; |
| 3727 expect(resultArguments, hasLength(1)); |
| 3728 expect(resultArguments[0], parameter); |
| 3729 } |
| 3730 } |
| 3731 |
| 3732 @reflectiveTest |
| 3733 class LibraryElementImplTest extends EngineTestCase { |
| 3734 void test_creation() { |
| 3735 expect( |
| 3736 new LibraryElementImpl.forNode( |
| 3737 createAnalysisContext(), AstFactory.libraryIdentifier2(["l"])), |
| 3738 isNotNull); |
| 3739 } |
| 3740 |
| 3741 void test_getImportedLibraries() { |
| 3742 AnalysisContext context = createAnalysisContext(); |
| 3743 LibraryElementImpl library1 = ElementFactory.library(context, "l1"); |
| 3744 LibraryElementImpl library2 = ElementFactory.library(context, "l2"); |
| 3745 LibraryElementImpl library3 = ElementFactory.library(context, "l3"); |
| 3746 LibraryElementImpl library4 = ElementFactory.library(context, "l4"); |
| 3747 PrefixElement prefixA = |
| 3748 new PrefixElementImpl.forNode(AstFactory.identifier3("a")); |
| 3749 PrefixElement prefixB = |
| 3750 new PrefixElementImpl.forNode(AstFactory.identifier3("b")); |
| 3751 List<ImportElementImpl> imports = [ |
| 3752 ElementFactory.importFor(library2, null), |
| 3753 ElementFactory.importFor(library2, prefixB), |
| 3754 ElementFactory.importFor(library3, null), |
| 3755 ElementFactory.importFor(library3, prefixA), |
| 3756 ElementFactory.importFor(library3, prefixB), |
| 3757 ElementFactory.importFor(library4, prefixA) |
| 3758 ]; |
| 3759 library1.imports = imports; |
| 3760 List<LibraryElement> libraries = library1.importedLibraries; |
| 3761 expect(libraries, |
| 3762 unorderedEquals(<LibraryElement>[library2, library3, library4])); |
| 3763 } |
| 3764 |
| 3765 void test_getPrefixes() { |
| 3766 AnalysisContext context = createAnalysisContext(); |
| 3767 LibraryElementImpl library = ElementFactory.library(context, "l1"); |
| 3768 PrefixElement prefixA = |
| 3769 new PrefixElementImpl.forNode(AstFactory.identifier3("a")); |
| 3770 PrefixElement prefixB = |
| 3771 new PrefixElementImpl.forNode(AstFactory.identifier3("b")); |
| 3772 List<ImportElementImpl> imports = [ |
| 3773 ElementFactory.importFor(ElementFactory.library(context, "l2"), null), |
| 3774 ElementFactory.importFor(ElementFactory.library(context, "l3"), null), |
| 3775 ElementFactory.importFor(ElementFactory.library(context, "l4"), prefixA), |
| 3776 ElementFactory.importFor(ElementFactory.library(context, "l5"), prefixA), |
| 3777 ElementFactory.importFor(ElementFactory.library(context, "l6"), prefixB) |
| 3778 ]; |
| 3779 library.imports = imports; |
| 3780 List<PrefixElement> prefixes = library.prefixes; |
| 3781 expect(prefixes, hasLength(2)); |
| 3782 if (identical(prefixA, prefixes[0])) { |
| 3783 expect(prefixes[1], same(prefixB)); |
| 3784 } else { |
| 3785 expect(prefixes[0], same(prefixB)); |
| 3786 expect(prefixes[1], same(prefixA)); |
| 3787 } |
| 3788 } |
| 3789 |
| 3790 void test_getUnits() { |
| 3791 AnalysisContext context = createAnalysisContext(); |
| 3792 LibraryElementImpl library = ElementFactory.library(context, "test"); |
| 3793 CompilationUnitElement unitLib = library.definingCompilationUnit; |
| 3794 CompilationUnitElementImpl unitA = |
| 3795 ElementFactory.compilationUnit("unit_a.dart", unitLib.source); |
| 3796 CompilationUnitElementImpl unitB = |
| 3797 ElementFactory.compilationUnit("unit_b.dart", unitLib.source); |
| 3798 library.parts = <CompilationUnitElement>[unitA, unitB]; |
| 3799 expect(library.units, |
| 3800 unorderedEquals(<CompilationUnitElement>[unitLib, unitA, unitB])); |
| 3801 } |
| 3802 |
| 3803 void test_getVisibleLibraries_cycle() { |
| 3804 AnalysisContext context = createAnalysisContext(); |
| 3805 LibraryElementImpl library = ElementFactory.library(context, "app"); |
| 3806 LibraryElementImpl libraryA = ElementFactory.library(context, "A"); |
| 3807 libraryA.imports = <ImportElementImpl>[ |
| 3808 ElementFactory.importFor(library, null) |
| 3809 ]; |
| 3810 library.imports = <ImportElementImpl>[ |
| 3811 ElementFactory.importFor(libraryA, null) |
| 3812 ]; |
| 3813 List<LibraryElement> libraries = library.visibleLibraries; |
| 3814 expect(libraries, unorderedEquals(<LibraryElement>[library, libraryA])); |
| 3815 } |
| 3816 |
| 3817 void test_getVisibleLibraries_directExports() { |
| 3818 AnalysisContext context = createAnalysisContext(); |
| 3819 LibraryElementImpl library = ElementFactory.library(context, "app"); |
| 3820 LibraryElementImpl libraryA = ElementFactory.library(context, "A"); |
| 3821 library.exports = <ExportElementImpl>[ElementFactory.exportFor(libraryA)]; |
| 3822 List<LibraryElement> libraries = library.visibleLibraries; |
| 3823 expect(libraries, unorderedEquals(<LibraryElement>[library])); |
| 3824 } |
| 3825 |
| 3826 void test_getVisibleLibraries_directImports() { |
| 3827 AnalysisContext context = createAnalysisContext(); |
| 3828 LibraryElementImpl library = ElementFactory.library(context, "app"); |
| 3829 LibraryElementImpl libraryA = ElementFactory.library(context, "A"); |
| 3830 library.imports = <ImportElementImpl>[ |
| 3831 ElementFactory.importFor(libraryA, null) |
| 3832 ]; |
| 3833 List<LibraryElement> libraries = library.visibleLibraries; |
| 3834 expect(libraries, unorderedEquals(<LibraryElement>[library, libraryA])); |
| 3835 } |
| 3836 |
| 3837 void test_getVisibleLibraries_indirectExports() { |
| 3838 AnalysisContext context = createAnalysisContext(); |
| 3839 LibraryElementImpl library = ElementFactory.library(context, "app"); |
| 3840 LibraryElementImpl libraryA = ElementFactory.library(context, "A"); |
| 3841 LibraryElementImpl libraryAA = ElementFactory.library(context, "AA"); |
| 3842 libraryA.exports = <ExportElementImpl>[ElementFactory.exportFor(libraryAA)]; |
| 3843 library.imports = <ImportElementImpl>[ |
| 3844 ElementFactory.importFor(libraryA, null) |
| 3845 ]; |
| 3846 List<LibraryElement> libraries = library.visibleLibraries; |
| 3847 expect(libraries, |
| 3848 unorderedEquals(<LibraryElement>[library, libraryA, libraryAA])); |
| 3849 } |
| 3850 |
| 3851 void test_getVisibleLibraries_indirectImports() { |
| 3852 AnalysisContext context = createAnalysisContext(); |
| 3853 LibraryElementImpl library = ElementFactory.library(context, "app"); |
| 3854 LibraryElementImpl libraryA = ElementFactory.library(context, "A"); |
| 3855 LibraryElementImpl libraryAA = ElementFactory.library(context, "AA"); |
| 3856 LibraryElementImpl libraryB = ElementFactory.library(context, "B"); |
| 3857 libraryA.imports = <ImportElementImpl>[ |
| 3858 ElementFactory.importFor(libraryAA, null) |
| 3859 ]; |
| 3860 library.imports = <ImportElementImpl>[ |
| 3861 ElementFactory.importFor(libraryA, null), |
| 3862 ElementFactory.importFor(libraryB, null) |
| 3863 ]; |
| 3864 List<LibraryElement> libraries = library.visibleLibraries; |
| 3865 expect( |
| 3866 libraries, |
| 3867 unorderedEquals( |
| 3868 <LibraryElement>[library, libraryA, libraryAA, libraryB])); |
| 3869 } |
| 3870 |
| 3871 void test_getVisibleLibraries_noImports() { |
| 3872 AnalysisContext context = createAnalysisContext(); |
| 3873 LibraryElementImpl library = ElementFactory.library(context, "app"); |
| 3874 expect( |
| 3875 library.visibleLibraries, unorderedEquals(<LibraryElement>[library])); |
| 3876 } |
| 3877 |
| 3878 void test_isUpToDate() { |
| 3879 AnalysisContext context = createAnalysisContext(); |
| 3880 context.sourceFactory = new SourceFactory([]); |
| 3881 LibraryElement library = ElementFactory.library(context, "foo"); |
| 3882 context.setContents(library.definingCompilationUnit.source, "sdfsdff"); |
| 3883 // Assert that we are not up to date if the target has an old time stamp. |
| 3884 expect(library.isUpToDate(0), isFalse); |
| 3885 // Assert that we are up to date with a target modification time in the |
| 3886 // future. |
| 3887 expect(library.isUpToDate(JavaSystem.currentTimeMillis() + 1000), isTrue); |
| 3888 } |
| 3889 |
| 3890 void test_setImports() { |
| 3891 AnalysisContext context = createAnalysisContext(); |
| 3892 LibraryElementImpl library = new LibraryElementImpl.forNode( |
| 3893 context, AstFactory.libraryIdentifier2(["l1"])); |
| 3894 List<ImportElementImpl> expectedImports = [ |
| 3895 ElementFactory.importFor(ElementFactory.library(context, "l2"), null), |
| 3896 ElementFactory.importFor(ElementFactory.library(context, "l3"), null) |
| 3897 ]; |
| 3898 library.imports = expectedImports; |
| 3899 List<ImportElement> actualImports = library.imports; |
| 3900 expect(actualImports, hasLength(expectedImports.length)); |
| 3901 for (int i = 0; i < actualImports.length; i++) { |
| 3902 expect(actualImports[i], same(expectedImports[i])); |
| 3903 } |
| 3904 } |
| 3905 } |
| 3906 |
| 3907 @reflectiveTest |
| 3908 class MethodElementImplTest extends EngineTestCase { |
| 3909 void test_computeNode() { |
| 3910 AnalysisContextHelper contextHelper = new AnalysisContextHelper(); |
| 3911 AnalysisContext context = contextHelper.context; |
| 3912 Source source = contextHelper.addSource( |
| 3913 "/test.dart", |
| 3914 r''' |
| 3915 abstract class A { |
| 3916 String m1() => null; |
| 3917 m2(); |
| 3918 } |
| 3919 '''); |
| 3920 // prepare CompilationUnitElement |
| 3921 LibraryElement libraryElement = context.computeLibraryElement(source); |
| 3922 CompilationUnitElement unitElement = libraryElement.definingCompilationUnit; |
| 3923 // m1 |
| 3924 { |
| 3925 MethodElement m1Element = unitElement.getType("A").getMethod('m1'); |
| 3926 MethodDeclaration m1Node = m1Element.computeNode(); |
| 3927 expect(m1Node, isNotNull); |
| 3928 expect(m1Node.name.name, "m1"); |
| 3929 expect(m1Node.element, same(m1Element)); |
| 3930 } |
| 3931 // m2 |
| 3932 { |
| 3933 MethodElement m2Element = unitElement.getType("A").getMethod('m2'); |
| 3934 MethodDeclaration m2Node = m2Element.computeNode(); |
| 3935 expect(m2Node, isNotNull); |
| 3936 expect(m2Node.name.name, "m2"); |
| 3937 expect(m2Node.element, same(m2Element)); |
| 3938 } |
| 3939 } |
| 3940 |
| 3941 void test_computeNode_withoutFunctionBody() { |
| 3942 AnalysisOptionsImpl options = new AnalysisOptionsImpl(); |
| 3943 options.analyzeFunctionBodies = false; |
| 3944 AnalysisContextHelper contextHelper = new AnalysisContextHelper(options); |
| 3945 AnalysisContext context = contextHelper.context; |
| 3946 Source source = contextHelper.addSource( |
| 3947 "/test.dart", |
| 3948 r''' |
| 3949 abstract class A { |
| 3950 String m1() => null; |
| 3951 m2(); |
| 3952 } |
| 3953 '''); |
| 3954 // prepare CompilationUnitElement |
| 3955 LibraryElement libraryElement = context.computeLibraryElement(source); |
| 3956 CompilationUnitElement unitElement = libraryElement.definingCompilationUnit; |
| 3957 // m1 |
| 3958 { |
| 3959 MethodElement m1Element = unitElement.getType("A").getMethod('m1'); |
| 3960 MethodDeclaration m1Node = m1Element.computeNode(); |
| 3961 expect(m1Node, isNotNull); |
| 3962 expect(m1Node.name.name, "m1"); |
| 3963 expect(m1Node.element, same(m1Element)); |
| 3964 } |
| 3965 // m2 |
| 3966 { |
| 3967 MethodElement m2Element = unitElement.getType("A").getMethod('m2'); |
| 3968 MethodDeclaration m2Node = m2Element.computeNode(); |
| 3969 expect(m2Node, isNotNull); |
| 3970 expect(m2Node.name.name, "m2"); |
| 3971 expect(m2Node.element, same(m2Element)); |
| 3972 } |
| 3973 } |
| 3974 } |
| 3975 |
| 3976 @reflectiveTest |
| 3977 class MultiplyDefinedElementImplTest extends EngineTestCase { |
| 3978 void test_fromElements_conflicting() { |
| 3979 Element firstElement = ElementFactory.localVariableElement2("xx"); |
| 3980 Element secondElement = ElementFactory.localVariableElement2("yy"); |
| 3981 Element result = MultiplyDefinedElementImpl.fromElements( |
| 3982 null, firstElement, secondElement); |
| 3983 EngineTestCase.assertInstanceOf( |
| 3984 (obj) => obj is MultiplyDefinedElement, MultiplyDefinedElement, result); |
| 3985 List<Element> elements = |
| 3986 (result as MultiplyDefinedElement).conflictingElements; |
| 3987 expect(elements, hasLength(2)); |
| 3988 for (int i = 0; i < elements.length; i++) { |
| 3989 EngineTestCase.assertInstanceOf((obj) => obj is LocalVariableElement, |
| 3990 LocalVariableElement, elements[i]); |
| 3991 } |
| 3992 } |
| 3993 |
| 3994 void test_fromElements_multiple() { |
| 3995 Element firstElement = ElementFactory.localVariableElement2("xx"); |
| 3996 Element secondElement = ElementFactory.localVariableElement2("yy"); |
| 3997 Element thirdElement = ElementFactory.localVariableElement2("zz"); |
| 3998 Element result = MultiplyDefinedElementImpl.fromElements( |
| 3999 null, |
| 4000 MultiplyDefinedElementImpl.fromElements( |
| 4001 null, firstElement, secondElement), |
| 4002 thirdElement); |
| 4003 EngineTestCase.assertInstanceOf( |
| 4004 (obj) => obj is MultiplyDefinedElement, MultiplyDefinedElement, result); |
| 4005 List<Element> elements = |
| 4006 (result as MultiplyDefinedElement).conflictingElements; |
| 4007 expect(elements, hasLength(3)); |
| 4008 for (int i = 0; i < elements.length; i++) { |
| 4009 EngineTestCase.assertInstanceOf((obj) => obj is LocalVariableElement, |
| 4010 LocalVariableElement, elements[i]); |
| 4011 } |
| 4012 } |
| 4013 |
| 4014 void test_fromElements_nonConflicting() { |
| 4015 Element element = ElementFactory.localVariableElement2("xx"); |
| 4016 expect(MultiplyDefinedElementImpl.fromElements(null, element, element), |
| 4017 same(element)); |
| 4018 } |
| 4019 } |
| 4020 |
| 4021 @reflectiveTest |
| 4022 class ParameterElementImplTest extends EngineTestCase { |
| 4023 void test_computeNode_DefaultFormalParameter() { |
| 4024 AnalysisContextHelper contextHelper = new AnalysisContextHelper(); |
| 4025 AnalysisContext context = contextHelper.context; |
| 4026 Source source = contextHelper.addSource( |
| 4027 "/test.dart", |
| 4028 r''' |
| 4029 main([int p = 42]) { |
| 4030 }'''); |
| 4031 // prepare CompilationUnitElement |
| 4032 LibraryElement libraryElement = context.computeLibraryElement(source); |
| 4033 CompilationUnitElement unitElement = libraryElement.definingCompilationUnit; |
| 4034 // p |
| 4035 { |
| 4036 ParameterElement element = unitElement.functions[0].parameters[0]; |
| 4037 DefaultFormalParameter node = element.computeNode(); |
| 4038 expect(node, isNotNull); |
| 4039 expect(node.identifier.name, 'p'); |
| 4040 expect(node.element, same(element)); |
| 4041 } |
| 4042 } |
| 4043 |
| 4044 void test_computeNode_FieldFormalParameter() { |
| 4045 AnalysisContextHelper contextHelper = new AnalysisContextHelper(); |
| 4046 AnalysisContext context = contextHelper.context; |
| 4047 Source source = contextHelper.addSource( |
| 4048 "/test.dart", |
| 4049 r''' |
| 4050 class A { |
| 4051 int p; |
| 4052 A(this.p) { |
| 4053 } |
| 4054 }'''); |
| 4055 // prepare CompilationUnitElement |
| 4056 LibraryElement libraryElement = context.computeLibraryElement(source); |
| 4057 CompilationUnitElement unitElement = libraryElement.definingCompilationUnit; |
| 4058 // p |
| 4059 { |
| 4060 ClassElement classA = unitElement.types[0]; |
| 4061 ConstructorElement constructorA = classA.constructors[0]; |
| 4062 FieldFormalParameterElement element = constructorA.parameters[0]; |
| 4063 FieldFormalParameter node = element.computeNode(); |
| 4064 expect(node, isNotNull); |
| 4065 expect(node.identifier.name, 'p'); |
| 4066 expect(node.element, same(element)); |
| 4067 } |
| 4068 } |
| 4069 |
| 4070 void test_computeNode_FunctionTypedFormalParameter() { |
| 4071 AnalysisContextHelper contextHelper = new AnalysisContextHelper(); |
| 4072 AnalysisContext context = contextHelper.context; |
| 4073 Source source = contextHelper.addSource( |
| 4074 "/test.dart", |
| 4075 r''' |
| 4076 main(p(int a, int b)) { |
| 4077 }'''); |
| 4078 // prepare CompilationUnitElement |
| 4079 LibraryElement libraryElement = context.computeLibraryElement(source); |
| 4080 CompilationUnitElement unitElement = libraryElement.definingCompilationUnit; |
| 4081 // p |
| 4082 { |
| 4083 ParameterElement element = unitElement.functions[0].parameters[0]; |
| 4084 FunctionTypedFormalParameter node = element.computeNode(); |
| 4085 expect(node, isNotNull); |
| 4086 expect(node.identifier.name, 'p'); |
| 4087 expect(node.element, same(element)); |
| 4088 } |
| 4089 } |
| 4090 |
| 4091 void test_computeNode_SimpleFormalParameter() { |
| 4092 AnalysisContextHelper contextHelper = new AnalysisContextHelper(); |
| 4093 AnalysisContext context = contextHelper.context; |
| 4094 Source source = contextHelper.addSource( |
| 4095 "/test.dart", |
| 4096 r''' |
| 4097 main(int p) { |
| 4098 }'''); |
| 4099 // prepare CompilationUnitElement |
| 4100 LibraryElement libraryElement = context.computeLibraryElement(source); |
| 4101 CompilationUnitElement unitElement = libraryElement.definingCompilationUnit; |
| 4102 // p |
| 4103 { |
| 4104 ParameterElement element = unitElement.functions[0].parameters[0]; |
| 4105 SimpleFormalParameter node = element.computeNode(); |
| 4106 expect(node, isNotNull); |
| 4107 expect(node.identifier.name, 'p'); |
| 4108 expect(node.element, same(element)); |
| 4109 } |
| 4110 } |
| 4111 } |
| 4112 |
| 4113 @reflectiveTest |
| 4114 class TypeParameterTypeImplTest extends EngineTestCase { |
| 4115 void test_creation() { |
| 4116 expect( |
| 4117 new TypeParameterTypeImpl( |
| 4118 new TypeParameterElementImpl.forNode(AstFactory.identifier3("E"))), |
| 4119 isNotNull); |
| 4120 } |
| 4121 |
| 4122 void test_getElement() { |
| 4123 TypeParameterElementImpl element = |
| 4124 new TypeParameterElementImpl.forNode(AstFactory.identifier3("E")); |
| 4125 TypeParameterTypeImpl type = new TypeParameterTypeImpl(element); |
| 4126 expect(type.element, element); |
| 4127 } |
| 4128 |
| 4129 void test_isMoreSpecificThan_typeArguments_dynamic() { |
| 4130 TypeParameterElementImpl element = |
| 4131 new TypeParameterElementImpl.forNode(AstFactory.identifier3("E")); |
| 4132 TypeParameterTypeImpl type = new TypeParameterTypeImpl(element); |
| 4133 // E << dynamic |
| 4134 expect(type.isMoreSpecificThan(DynamicTypeImpl.instance), isTrue); |
| 4135 } |
| 4136 |
| 4137 void test_isMoreSpecificThan_typeArguments_object() { |
| 4138 TypeParameterElementImpl element = |
| 4139 new TypeParameterElementImpl.forNode(AstFactory.identifier3("E")); |
| 4140 TypeParameterTypeImpl type = new TypeParameterTypeImpl(element); |
| 4141 // E << Object |
| 4142 expect(type.isMoreSpecificThan(ElementFactory.object.type), isTrue); |
| 4143 } |
| 4144 |
| 4145 void test_isMoreSpecificThan_typeArguments_resursive() { |
| 4146 ClassElementImpl classS = ElementFactory.classElement2("A"); |
| 4147 TypeParameterElementImpl typeParameterU = |
| 4148 new TypeParameterElementImpl.forNode(AstFactory.identifier3("U")); |
| 4149 TypeParameterTypeImpl typeParameterTypeU = |
| 4150 new TypeParameterTypeImpl(typeParameterU); |
| 4151 TypeParameterElementImpl typeParameterT = |
| 4152 new TypeParameterElementImpl.forNode(AstFactory.identifier3("T")); |
| 4153 TypeParameterTypeImpl typeParameterTypeT = |
| 4154 new TypeParameterTypeImpl(typeParameterT); |
| 4155 typeParameterT.bound = typeParameterTypeU; |
| 4156 typeParameterU.bound = typeParameterTypeU; |
| 4157 // <T extends U> and <U extends T> |
| 4158 // T << S |
| 4159 expect(typeParameterTypeT.isMoreSpecificThan(classS.type), isFalse); |
| 4160 } |
| 4161 |
| 4162 void test_isMoreSpecificThan_typeArguments_self() { |
| 4163 TypeParameterElementImpl element = |
| 4164 new TypeParameterElementImpl.forNode(AstFactory.identifier3("E")); |
| 4165 TypeParameterTypeImpl type = new TypeParameterTypeImpl(element); |
| 4166 // E << E |
| 4167 expect(type.isMoreSpecificThan(type), isTrue); |
| 4168 } |
| 4169 |
| 4170 void test_isMoreSpecificThan_typeArguments_transitivity_interfaceTypes() { |
| 4171 // class A {} |
| 4172 // class B extends A {} |
| 4173 // |
| 4174 ClassElement classA = ElementFactory.classElement2("A"); |
| 4175 ClassElement classB = ElementFactory.classElement("B", classA.type); |
| 4176 InterfaceType typeA = classA.type; |
| 4177 InterfaceType typeB = classB.type; |
| 4178 TypeParameterElementImpl typeParameterT = |
| 4179 new TypeParameterElementImpl.forNode(AstFactory.identifier3("T")); |
| 4180 typeParameterT.bound = typeB; |
| 4181 TypeParameterTypeImpl typeParameterTypeT = |
| 4182 new TypeParameterTypeImpl(typeParameterT); |
| 4183 // <T extends B> |
| 4184 // T << A |
| 4185 expect(typeParameterTypeT.isMoreSpecificThan(typeA), isTrue); |
| 4186 } |
| 4187 |
| 4188 void test_isMoreSpecificThan_typeArguments_transitivity_typeParameters() { |
| 4189 ClassElementImpl classS = ElementFactory.classElement2("A"); |
| 4190 TypeParameterElementImpl typeParameterU = |
| 4191 new TypeParameterElementImpl.forNode(AstFactory.identifier3("U")); |
| 4192 typeParameterU.bound = classS.type; |
| 4193 TypeParameterTypeImpl typeParameterTypeU = |
| 4194 new TypeParameterTypeImpl(typeParameterU); |
| 4195 TypeParameterElementImpl typeParameterT = |
| 4196 new TypeParameterElementImpl.forNode(AstFactory.identifier3("T")); |
| 4197 typeParameterT.bound = typeParameterTypeU; |
| 4198 TypeParameterTypeImpl typeParameterTypeT = |
| 4199 new TypeParameterTypeImpl(typeParameterT); |
| 4200 // <T extends U> and <U extends S> |
| 4201 // T << S |
| 4202 expect(typeParameterTypeT.isMoreSpecificThan(classS.type), isTrue); |
| 4203 } |
| 4204 |
| 4205 void test_isMoreSpecificThan_typeArguments_upperBound() { |
| 4206 ClassElementImpl classS = ElementFactory.classElement2("A"); |
| 4207 TypeParameterElementImpl typeParameterT = |
| 4208 new TypeParameterElementImpl.forNode(AstFactory.identifier3("T")); |
| 4209 typeParameterT.bound = classS.type; |
| 4210 TypeParameterTypeImpl typeParameterTypeT = |
| 4211 new TypeParameterTypeImpl(typeParameterT); |
| 4212 // <T extends S> |
| 4213 // T << S |
| 4214 expect(typeParameterTypeT.isMoreSpecificThan(classS.type), isTrue); |
| 4215 } |
| 4216 |
| 4217 void test_substitute_equal() { |
| 4218 TypeParameterElementImpl element = |
| 4219 new TypeParameterElementImpl.forNode(AstFactory.identifier3("E")); |
| 4220 TypeParameterTypeImpl type = new TypeParameterTypeImpl(element); |
| 4221 InterfaceTypeImpl argument = new InterfaceTypeImpl( |
| 4222 new ClassElementImpl.forNode(AstFactory.identifier3("A"))); |
| 4223 TypeParameterTypeImpl parameter = new TypeParameterTypeImpl(element); |
| 4224 expect(type.substitute2(<DartType>[argument], <DartType>[parameter]), |
| 4225 same(argument)); |
| 4226 } |
| 4227 |
| 4228 void test_substitute_notEqual() { |
| 4229 TypeParameterTypeImpl type = new TypeParameterTypeImpl( |
| 4230 new TypeParameterElementImpl.forNode(AstFactory.identifier3("E"))); |
| 4231 InterfaceTypeImpl argument = new InterfaceTypeImpl( |
| 4232 new ClassElementImpl.forNode(AstFactory.identifier3("A"))); |
| 4233 TypeParameterTypeImpl parameter = new TypeParameterTypeImpl( |
| 4234 new TypeParameterElementImpl.forNode(AstFactory.identifier3("F"))); |
| 4235 expect(type.substitute2(<DartType>[argument], <DartType>[parameter]), |
| 4236 same(type)); |
| 4237 } |
| 4238 } |
| 4239 |
| 4240 @reflectiveTest |
| 4241 class VoidTypeImplTest extends EngineTestCase { |
| 4242 /** |
| 4243 * Reference {code VoidTypeImpl.getInstance()}. |
| 4244 */ |
| 4245 DartType _voidType = VoidTypeImpl.instance; |
| 4246 |
| 4247 void test_isMoreSpecificThan_void_A() { |
| 4248 ClassElement classA = ElementFactory.classElement2("A"); |
| 4249 expect(_voidType.isMoreSpecificThan(classA.type), isFalse); |
| 4250 } |
| 4251 |
| 4252 void test_isMoreSpecificThan_void_dynamic() { |
| 4253 expect(_voidType.isMoreSpecificThan(DynamicTypeImpl.instance), isTrue); |
| 4254 } |
| 4255 |
| 4256 void test_isMoreSpecificThan_void_void() { |
| 4257 expect(_voidType.isMoreSpecificThan(_voidType), isTrue); |
| 4258 } |
| 4259 |
| 4260 void test_isSubtypeOf_void_A() { |
| 4261 ClassElement classA = ElementFactory.classElement2("A"); |
| 4262 expect(_voidType.isSubtypeOf(classA.type), isFalse); |
| 4263 } |
| 4264 |
| 4265 void test_isSubtypeOf_void_dynamic() { |
| 4266 expect(_voidType.isSubtypeOf(DynamicTypeImpl.instance), isTrue); |
| 4267 } |
| 4268 |
| 4269 void test_isSubtypeOf_void_void() { |
| 4270 expect(_voidType.isSubtypeOf(_voidType), isTrue); |
| 4271 } |
| 4272 |
| 4273 void test_isVoid() { |
| 4274 expect(_voidType.isVoid, isTrue); |
| 4275 } |
| 4276 } |
| 4277 |
| 4278 class _FunctionTypeImplTest_isSubtypeOf_baseCase_classFunction |
| 4279 extends InterfaceTypeImpl { |
| 4280 _FunctionTypeImplTest_isSubtypeOf_baseCase_classFunction(ClassElement arg0) |
| 4281 : super(arg0); |
| 4282 |
| 4283 @override |
| 4284 bool get isDartCoreFunction => true; |
| 4285 } |
OLD | NEW |