| OLD | NEW |
| 1 // Copyright (c) 2015, the Dart project authors. Please see the AUTHORS file | 1 // Copyright (c) 2015, the Dart project authors. Please see the AUTHORS file |
| 2 // for details. All rights reserved. Use of this source code is governed by a | 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. | 3 // BSD-style license that can be found in the LICENSE file. |
| 4 | 4 |
| 5 library test.src.serialization.elements_test; | 5 library test.src.serialization.elements_test; |
| 6 | 6 |
| 7 import 'package:analyzer/dart/element/element.dart'; | 7 import 'package:analyzer/dart/element/element.dart'; |
| 8 import 'package:analyzer/dart/element/type.dart'; | 8 import 'package:analyzer/dart/element/type.dart'; |
| 9 import 'package:analyzer/src/dart/element/element.dart'; | 9 import 'package:analyzer/src/dart/element/element.dart'; |
| 10 import 'package:analyzer/src/dart/element/type.dart'; | 10 import 'package:analyzer/src/dart/element/type.dart'; |
| (...skipping 29 matching lines...) Expand all Loading... |
| 40 otherLibrarySources.add(analysisContext2.sourceFactory.forUri(uri)); | 40 otherLibrarySources.add(analysisContext2.sourceFactory.forUri(uri)); |
| 41 } | 41 } |
| 42 | 42 |
| 43 void addLibrarySource(String filePath, String contents) { | 43 void addLibrarySource(String filePath, String contents) { |
| 44 otherLibrarySources.add(addNamedSource(filePath, contents)); | 44 otherLibrarySources.add(addNamedSource(filePath, contents)); |
| 45 } | 45 } |
| 46 | 46 |
| 47 void checkLibrary(String text, {bool allowErrors: false}) { | 47 void checkLibrary(String text, {bool allowErrors: false}) { |
| 48 Source source = addSource(text); | 48 Source source = addSource(text); |
| 49 LibraryElementImpl original = resolve2(source); | 49 LibraryElementImpl original = resolve2(source); |
| 50 LibraryElementImpl resynthesized = | 50 LibraryElementImpl resynthesized = resynthesizeLibraryElement( |
| 51 resynthesizeLibrary(source, original, allowErrors); | 51 encodeLibrary(original, allowErrors: allowErrors), |
| 52 source.uri.toString()); |
| 52 checkLibraryElements(original, resynthesized); | 53 checkLibraryElements(original, resynthesized); |
| 53 } | 54 } |
| 54 | 55 |
| 55 void checkLibraryElements( | 56 void checkLibraryElements( |
| 56 LibraryElementImpl original, LibraryElementImpl resynthesized) { | 57 LibraryElementImpl original, LibraryElementImpl resynthesized) { |
| 57 compareElements(resynthesized, original, '(library)'); | 58 compareElements(resynthesized, original, '(library)'); |
| 58 expect(resynthesized.displayName, original.displayName); | 59 expect(resynthesized.displayName, original.displayName); |
| 59 expect(original.enclosingElement, isNull); | 60 expect(original.enclosingElement, isNull); |
| 60 expect(resynthesized.enclosingElement, isNull); | 61 expect(resynthesized.enclosingElement, isNull); |
| 61 expect(resynthesized.hasExtUri, original.hasExtUri); | 62 expect(resynthesized.hasExtUri, original.hasExtUri); |
| (...skipping 442 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 504 expect(resynthesized.uriEnd, original.uriEnd, reason: desc); | 505 expect(resynthesized.uriEnd, original.uriEnd, reason: desc); |
| 505 } | 506 } |
| 506 | 507 |
| 507 void compareVariableElements(VariableElementImpl resynthesized, | 508 void compareVariableElements(VariableElementImpl resynthesized, |
| 508 VariableElementImpl original, String desc) { | 509 VariableElementImpl original, String desc) { |
| 509 compareElements(resynthesized, original, desc); | 510 compareElements(resynthesized, original, desc); |
| 510 compareTypes(resynthesized.type, original.type, desc); | 511 compareTypes(resynthesized.type, original.type, desc); |
| 511 // TODO(paulberry): test initializer | 512 // TODO(paulberry): test initializer |
| 512 } | 513 } |
| 513 | 514 |
| 514 fail_library_hasExtUri() { | 515 /** |
| 515 checkLibrary('import "dart-ext:doesNotExist.dart";'); | 516 * Serialize the given [library] into a summary. Then create a |
| 517 * [_TestSummaryResynthesizer] which can deserialize it, along with any |
| 518 * references it makes to `dart:core`. |
| 519 * |
| 520 * Errors will lead to a test failure unless [allowErrors] is `true`. |
| 521 */ |
| 522 _TestSummaryResynthesizer encodeLibrary(LibraryElementImpl library, |
| 523 {bool allowErrors: false}) { |
| 524 if (!allowErrors) { |
| 525 assertNoErrors(library.source); |
| 526 } |
| 527 addLibrary('dart:core'); |
| 528 return encodeLibraryElement(library); |
| 516 } | 529 } |
| 517 | 530 |
| 518 ElementImpl getActualElement(Element element, String desc) { | 531 /** |
| 519 if (element is ElementHandle) { | 532 * Convert the library element [library] into a summary, and then create a |
| 520 return element.actualElement; | 533 * [_TestSummaryResynthesizer] which can deserialize it. |
| 521 } else if (element is ElementImpl) { | 534 * |
| 522 return element; | 535 * Caller is responsible for checking the library for errors, and adding any |
| 523 } else { | 536 * dependent libraries using [addLibrary]. |
| 524 fail('Unexpected type for resynthesized ($desc):' | 537 */ |
| 525 ' ${element.runtimeType}'); | 538 _TestSummaryResynthesizer encodeLibraryElement(LibraryElementImpl library) { |
| 526 return null; | |
| 527 } | |
| 528 } | |
| 529 | |
| 530 LibraryElementImpl resynthesizeLibrary( | |
| 531 Source source, LibraryElementImpl original, bool allowErrors) { | |
| 532 if (!allowErrors) { | |
| 533 assertNoErrors(source); | |
| 534 } | |
| 535 String uri = source.uri.toString(); | |
| 536 addLibrary('dart:core'); | |
| 537 return resynthesizeLibraryElement(uri, original); | |
| 538 } | |
| 539 | |
| 540 LibraryElementImpl resynthesizeLibraryElement( | |
| 541 String uri, LibraryElementImpl original) { | |
| 542 Map<String, UnlinkedUnit> unlinkedSummaries = <String, UnlinkedUnit>{}; | 539 Map<String, UnlinkedUnit> unlinkedSummaries = <String, UnlinkedUnit>{}; |
| 543 LinkedLibrary getLinkedSummaryFor(LibraryElement lib) { | 540 LinkedLibrary getLinkedSummaryFor(LibraryElement lib) { |
| 544 LibrarySerializationResult serialized = serializeLibrary( | 541 LibrarySerializationResult serialized = serializeLibrary( |
| 545 lib, typeProvider, analysisContext.analysisOptions.strongMode); | 542 lib, typeProvider, analysisContext.analysisOptions.strongMode); |
| 546 for (int i = 0; i < serialized.unlinkedUnits.length; i++) { | 543 for (int i = 0; i < serialized.unlinkedUnits.length; i++) { |
| 547 unlinkedSummaries[serialized.unitUris[i]] = | 544 unlinkedSummaries[serialized.unitUris[i]] = |
| 548 new UnlinkedUnit.fromBuffer(serialized.unlinkedUnits[i].toBuffer()); | 545 new UnlinkedUnit.fromBuffer(serialized.unlinkedUnits[i].toBuffer()); |
| 549 } | 546 } |
| 550 return new LinkedLibrary.fromBuffer(serialized.linked.toBuffer()); | 547 return new LinkedLibrary.fromBuffer(serialized.linked.toBuffer()); |
| 551 } | 548 } |
| 552 Map<String, LinkedLibrary> linkedSummaries = <String, LinkedLibrary>{ | 549 Map<String, LinkedLibrary> linkedSummaries = <String, LinkedLibrary>{ |
| 553 uri: getLinkedSummaryFor(original) | 550 library.source.uri.toString(): getLinkedSummaryFor(library) |
| 554 }; | 551 }; |
| 555 for (Source source in otherLibrarySources) { | 552 for (Source source in otherLibrarySources) { |
| 556 LibraryElement original = resolve2(source); | 553 LibraryElement original = resolve2(source); |
| 557 String uri = source.uri.toString(); | 554 String uri = source.uri.toString(); |
| 558 linkedSummaries[uri] = getLinkedSummaryFor(original); | 555 linkedSummaries[uri] = getLinkedSummaryFor(original); |
| 559 } | 556 } |
| 560 _TestSummaryResynthesizer resynthesizer = new _TestSummaryResynthesizer( | 557 return new _TestSummaryResynthesizer( |
| 561 null, | 558 null, |
| 562 analysisContext, | 559 analysisContext, |
| 563 analysisContext.typeProvider, | 560 analysisContext.typeProvider, |
| 564 analysisContext.sourceFactory, | 561 analysisContext.sourceFactory, |
| 565 unlinkedSummaries, | 562 unlinkedSummaries, |
| 566 linkedSummaries, | 563 linkedSummaries, |
| 567 options.strongMode); | 564 options.strongMode); |
| 565 } |
| 566 |
| 567 fail_library_hasExtUri() { |
| 568 checkLibrary('import "dart-ext:doesNotExist.dart";'); |
| 569 } |
| 570 |
| 571 ElementImpl getActualElement(Element element, String desc) { |
| 572 if (element is ElementHandle) { |
| 573 return element.actualElement; |
| 574 } else if (element is ElementImpl) { |
| 575 return element; |
| 576 } else { |
| 577 fail('Unexpected type for resynthesized ($desc):' |
| 578 ' ${element.runtimeType}'); |
| 579 return null; |
| 580 } |
| 581 } |
| 582 |
| 583 /** |
| 584 * Resynthesize the library element associated with [uri] using |
| 585 * [resynthesizer], and verify that it only had to consult one summary in |
| 586 * order to do so. |
| 587 */ |
| 588 LibraryElementImpl resynthesizeLibraryElement( |
| 589 _TestSummaryResynthesizer resynthesizer, String uri) { |
| 568 LibraryElementImpl resynthesized = resynthesizer.getLibraryElement(uri); | 590 LibraryElementImpl resynthesized = resynthesizer.getLibraryElement(uri); |
| 569 // Check that no other summaries needed to be resynthesized to resynthesize | 591 // Check that no other summaries needed to be resynthesized to resynthesize |
| 570 // the library element. | 592 // the library element. |
| 571 expect(resynthesizer.resynthesisCount, 1); | 593 expect(resynthesizer.resynthesisCount, 1); |
| 572 return resynthesized; | 594 return resynthesized; |
| 573 } | 595 } |
| 574 | 596 |
| 575 @override | 597 @override |
| 576 void setUp() { | 598 void setUp() { |
| 577 super.setUp(); | 599 super.setUp(); |
| (...skipping 320 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 898 */ | 920 */ |
| 899 C(); | 921 C(); |
| 900 }'''); | 922 }'''); |
| 901 } | 923 } |
| 902 | 924 |
| 903 test_core() { | 925 test_core() { |
| 904 String uri = 'dart:core'; | 926 String uri = 'dart:core'; |
| 905 LibraryElementImpl original = | 927 LibraryElementImpl original = |
| 906 resolve2(analysisContext2.sourceFactory.forUri(uri)); | 928 resolve2(analysisContext2.sourceFactory.forUri(uri)); |
| 907 LibraryElementImpl resynthesized = | 929 LibraryElementImpl resynthesized = |
| 908 resynthesizeLibraryElement(uri, original); | 930 resynthesizeLibraryElement(encodeLibraryElement(original), uri); |
| 909 checkLibraryElements(original, resynthesized); | 931 checkLibraryElements(original, resynthesized); |
| 910 } | 932 } |
| 911 | 933 |
| 912 test_enum_documented() { | 934 test_enum_documented() { |
| 913 checkLibrary(''' | 935 checkLibrary(''' |
| 914 // Extra comment so doc comment offset != 0 | 936 // Extra comment so doc comment offset != 0 |
| 915 /** | 937 /** |
| 916 * Docs | 938 * Docs |
| 917 */ | 939 */ |
| 918 enum E { v }'''); | 940 enum E { v }'''); |
| (...skipping 241 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1160 | 1182 |
| 1161 test_function_type_parameter_with_function_typed_parameter() { | 1183 test_function_type_parameter_with_function_typed_parameter() { |
| 1162 resetWithOptions(new AnalysisOptionsImpl()..enableGenericMethods = true); | 1184 resetWithOptions(new AnalysisOptionsImpl()..enableGenericMethods = true); |
| 1163 checkLibrary('void f<T, U>(T x(U u)) {}'); | 1185 checkLibrary('void f<T, U>(T x(U u)) {}'); |
| 1164 } | 1186 } |
| 1165 | 1187 |
| 1166 test_functions() { | 1188 test_functions() { |
| 1167 checkLibrary('f() {} g() {}'); | 1189 checkLibrary('f() {} g() {}'); |
| 1168 } | 1190 } |
| 1169 | 1191 |
| 1192 test_getElement_constructor_named() { |
| 1193 ConstructorElement original = resolve2(addSource('class C { C.named(); }')) |
| 1194 .getType('C') |
| 1195 .getNamedConstructor('named'); |
| 1196 expect(original, isNotNull); |
| 1197 ConstructorElement resynthesized = validateGetElement(original); |
| 1198 compareConstructorElements(resynthesized, original, 'C.constructor named'); |
| 1199 } |
| 1200 |
| 1201 test_getElement_constructor_unnamed() { |
| 1202 ConstructorElement original = |
| 1203 resolve2(addSource('class C { C(); }')).getType('C').unnamedConstructor; |
| 1204 expect(original, isNotNull); |
| 1205 ConstructorElement resynthesized = validateGetElement(original); |
| 1206 compareConstructorElements(resynthesized, original, 'C.constructor'); |
| 1207 } |
| 1208 |
| 1209 test_getElement_field() { |
| 1210 FieldElement original = |
| 1211 resolve2(addSource('class C { var f; }')).getType('C').getField('f'); |
| 1212 expect(original, isNotNull); |
| 1213 FieldElement resynthesized = validateGetElement(original); |
| 1214 compareFieldElements(resynthesized, original, 'C.field f'); |
| 1215 } |
| 1216 |
| 1217 test_getElement_getter() { |
| 1218 PropertyAccessorElement original = |
| 1219 resolve2(addSource('class C { get f => null; }')) |
| 1220 .getType('C') |
| 1221 .getGetter('f'); |
| 1222 expect(original, isNotNull); |
| 1223 PropertyAccessorElement resynthesized = validateGetElement(original); |
| 1224 comparePropertyAccessorElements(resynthesized, original, 'C.getter f'); |
| 1225 } |
| 1226 |
| 1227 test_getElement_method() { |
| 1228 MethodElement original = |
| 1229 resolve2(addSource('class C { f() {} }')).getType('C').getMethod('f'); |
| 1230 expect(original, isNotNull); |
| 1231 MethodElement resynthesized = validateGetElement(original); |
| 1232 compareMethodElements(resynthesized, original, 'C.method f'); |
| 1233 } |
| 1234 |
| 1235 test_getElement_operator() { |
| 1236 MethodElement original = |
| 1237 resolve2(addSource('class C { operator+(x) => null; }')) |
| 1238 .getType('C') |
| 1239 .getMethod('+'); |
| 1240 expect(original, isNotNull); |
| 1241 MethodElement resynthesized = validateGetElement(original); |
| 1242 compareMethodElements(resynthesized, original, 'C.operator+'); |
| 1243 } |
| 1244 |
| 1245 test_getElement_setter() { |
| 1246 PropertyAccessorElement original = |
| 1247 resolve2(addSource('class C { void set f(value) {} }')) |
| 1248 .getType('C') |
| 1249 .getSetter('f'); |
| 1250 expect(original, isNotNull); |
| 1251 PropertyAccessorElement resynthesized = validateGetElement(original); |
| 1252 comparePropertyAccessorElements(resynthesized, original, 'C.setter f'); |
| 1253 } |
| 1254 |
| 1170 test_getter_documented() { | 1255 test_getter_documented() { |
| 1171 checkLibrary(''' | 1256 checkLibrary(''' |
| 1172 // Extra comment so doc comment offset != 0 | 1257 // Extra comment so doc comment offset != 0 |
| 1173 /** | 1258 /** |
| 1174 * Docs | 1259 * Docs |
| 1175 */ | 1260 */ |
| 1176 get x => null;'''); | 1261 get x => null;'''); |
| 1177 } | 1262 } |
| 1178 | 1263 |
| 1179 test_getter_external() { | 1264 test_getter_external() { |
| (...skipping 532 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1712 | 1797 |
| 1713 test_variable_setterInPart_getterInPart() { | 1798 test_variable_setterInPart_getterInPart() { |
| 1714 addNamedSource('/a.dart', 'part of my.lib; void set x(int _) {}'); | 1799 addNamedSource('/a.dart', 'part of my.lib; void set x(int _) {}'); |
| 1715 addNamedSource('/b.dart', 'part of my.lib; int get x => 42;'); | 1800 addNamedSource('/b.dart', 'part of my.lib; int get x => 42;'); |
| 1716 checkLibrary('library my.lib; part "a.dart"; part "b.dart";'); | 1801 checkLibrary('library my.lib; part "a.dart"; part "b.dart";'); |
| 1717 } | 1802 } |
| 1718 | 1803 |
| 1719 test_variables() { | 1804 test_variables() { |
| 1720 checkLibrary('int i; int j;'); | 1805 checkLibrary('int i; int j;'); |
| 1721 } | 1806 } |
| 1807 |
| 1808 /** |
| 1809 * Encode the library containing [original] into a summary and then use |
| 1810 * [_TestSummaryResynthesizer.getElement] to retrieve just the original |
| 1811 * element from the resynthesized summary. |
| 1812 */ |
| 1813 Element validateGetElement(Element original) { |
| 1814 _TestSummaryResynthesizer resynthesizer = encodeLibrary(original.library); |
| 1815 ElementLocationImpl location = original.location; |
| 1816 Element result = resynthesizer.getElement(location); |
| 1817 // Check that no other summaries needed to be resynthesized to resynthesize |
| 1818 // the library element. |
| 1819 expect(resynthesizer.resynthesisCount, 1); |
| 1820 expect(result.location, location); |
| 1821 return result; |
| 1822 } |
| 1722 } | 1823 } |
| 1723 | 1824 |
| 1724 class _TestSummaryResynthesizer extends SummaryResynthesizer { | 1825 class _TestSummaryResynthesizer extends SummaryResynthesizer { |
| 1725 final Map<String, UnlinkedUnit> unlinkedSummaries; | 1826 final Map<String, UnlinkedUnit> unlinkedSummaries; |
| 1726 final Map<String, LinkedLibrary> linkedSummaries; | 1827 final Map<String, LinkedLibrary> linkedSummaries; |
| 1727 | 1828 |
| 1728 _TestSummaryResynthesizer( | 1829 _TestSummaryResynthesizer( |
| 1729 SummaryResynthesizer parent, | 1830 SummaryResynthesizer parent, |
| 1730 AnalysisContext context, | 1831 AnalysisContext context, |
| 1731 TypeProvider typeProvider, | 1832 TypeProvider typeProvider, |
| (...skipping 19 matching lines...) Expand all Loading... |
| 1751 fail('Unexpectedly tried to get unlinked summary for $uri'); | 1852 fail('Unexpectedly tried to get unlinked summary for $uri'); |
| 1752 } | 1853 } |
| 1753 return serializedUnit; | 1854 return serializedUnit; |
| 1754 } | 1855 } |
| 1755 | 1856 |
| 1756 @override | 1857 @override |
| 1757 bool hasLibrarySummary(String uri) { | 1858 bool hasLibrarySummary(String uri) { |
| 1758 return true; | 1859 return true; |
| 1759 } | 1860 } |
| 1760 } | 1861 } |
| OLD | NEW |