| 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 'dart:convert'; | |
| 8 | |
| 9 import 'package:analyzer/dart/ast/ast.dart'; | 7 import 'package:analyzer/dart/ast/ast.dart'; |
| 10 import 'package:analyzer/dart/constant/value.dart'; | 8 import 'package:analyzer/dart/constant/value.dart'; |
| 11 import 'package:analyzer/dart/element/element.dart'; | 9 import 'package:analyzer/dart/element/element.dart'; |
| 12 import 'package:analyzer/dart/element/type.dart'; | 10 import 'package:analyzer/dart/element/type.dart'; |
| 13 import 'package:analyzer/error/error.dart'; | 11 import 'package:analyzer/error/error.dart'; |
| 14 import 'package:analyzer/src/dart/ast/ast.dart'; | 12 import 'package:analyzer/src/dart/ast/ast.dart'; |
| 15 import 'package:analyzer/src/dart/element/element.dart'; | 13 import 'package:analyzer/src/dart/element/element.dart'; |
| 16 import 'package:analyzer/src/dart/element/handle.dart'; | 14 import 'package:analyzer/src/dart/element/handle.dart'; |
| 17 import 'package:analyzer/src/dart/element/member.dart'; | 15 import 'package:analyzer/src/dart/element/member.dart'; |
| 18 import 'package:analyzer/src/dart/element/type.dart'; | 16 import 'package:analyzer/src/dart/element/type.dart'; |
| 19 import 'package:analyzer/src/error/codes.dart'; | 17 import 'package:analyzer/src/error/codes.dart'; |
| 20 import 'package:analyzer/src/generated/engine.dart'; | 18 import 'package:analyzer/src/generated/engine.dart'; |
| 21 import 'package:analyzer/src/generated/resolver.dart' show Namespace; | 19 import 'package:analyzer/src/generated/resolver.dart' show Namespace; |
| 22 import 'package:analyzer/src/generated/sdk.dart'; | 20 import 'package:analyzer/src/generated/sdk.dart'; |
| 23 import 'package:analyzer/src/generated/source.dart'; | 21 import 'package:analyzer/src/generated/source.dart'; |
| 24 import 'package:analyzer/src/generated/testing/ast_factory.dart'; | 22 import 'package:analyzer/src/generated/testing/ast_factory.dart'; |
| 25 import 'package:analyzer/src/summary/idl.dart'; | 23 import 'package:analyzer/src/summary/idl.dart'; |
| 26 import 'package:analyzer/src/summary/resynthesize.dart'; | 24 import 'package:analyzer/src/summary/resynthesize.dart'; |
| 27 import 'package:analyzer/src/summary/summarize_elements.dart'; | |
| 28 import 'package:test_reflective_loader/test_reflective_loader.dart'; | 25 import 'package:test_reflective_loader/test_reflective_loader.dart'; |
| 29 import 'package:unittest/unittest.dart'; | 26 import 'package:unittest/unittest.dart'; |
| 30 | 27 |
| 31 import '../../generated/test_support.dart'; | 28 import '../../generated/test_support.dart'; |
| 32 import '../abstract_single_unit.dart'; | 29 import '../abstract_single_unit.dart'; |
| 33 import '../context/abstract_context.dart'; | 30 import '../context/abstract_context.dart'; |
| 34 import 'summary_common.dart' show canonicalize; | |
| 35 | |
| 36 main() { | |
| 37 groupSep = ' | '; | |
| 38 defineReflectiveTests(ResynthesizeElementTest); | |
| 39 } | |
| 40 | 31 |
| 41 /** | 32 /** |
| 42 * Abstract base class for resynthesizing and comparing elements. | 33 * Abstract base class for resynthesizing and comparing elements. |
| 43 */ | 34 */ |
| 44 abstract class AbstractResynthesizeTest extends AbstractSingleUnitTest { | 35 abstract class AbstractResynthesizeTest extends AbstractSingleUnitTest { |
| 45 Set<Source> otherLibrarySources = new Set<Source>(); | 36 Set<Source> otherLibrarySources = new Set<Source>(); |
| 46 | 37 |
| 47 /** | 38 /** |
| 48 * Names of variables which have initializers that are not valid constants, | 39 * Names of variables which have initializers that are not valid constants, |
| 49 * so they are not resynthesized. | 40 * so they are not resynthesized. |
| (...skipping 1078 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1128 } | 1119 } |
| 1129 | 1120 |
| 1130 DartSdk createDartSdk() => AbstractContextTest.SHARED_MOCK_SDK; | 1121 DartSdk createDartSdk() => AbstractContextTest.SHARED_MOCK_SDK; |
| 1131 | 1122 |
| 1132 /** | 1123 /** |
| 1133 * Determine the analysis options that should be used for this test. | 1124 * Determine the analysis options that should be used for this test. |
| 1134 */ | 1125 */ |
| 1135 AnalysisOptionsImpl createOptions() => | 1126 AnalysisOptionsImpl createOptions() => |
| 1136 new AnalysisOptionsImpl()..enableGenericMethods = true; | 1127 new AnalysisOptionsImpl()..enableGenericMethods = true; |
| 1137 | 1128 |
| 1138 /** | |
| 1139 * Serialize the given [library] into a summary. Then create a | |
| 1140 * [TestSummaryResynthesizer] which can deserialize it, along with any | |
| 1141 * references it makes to `dart:core`. | |
| 1142 * | |
| 1143 * Errors will lead to a test failure unless [allowErrors] is `true`. | |
| 1144 */ | |
| 1145 TestSummaryResynthesizer encodeLibrary(LibraryElementImpl library, | |
| 1146 {bool allowErrors: false, bool dumpSummaries: false}) { | |
| 1147 if (!allowErrors) { | |
| 1148 assertNoErrors(library.source); | |
| 1149 } | |
| 1150 addLibrary('dart:core'); | |
| 1151 addLibrary('dart:async'); | |
| 1152 addLibrary('dart:math'); | |
| 1153 return encodeLibraryElement(library, dumpSummaries: dumpSummaries); | |
| 1154 } | |
| 1155 | |
| 1156 /** | |
| 1157 * Convert the library element [library] into a summary, and then create a | |
| 1158 * [TestSummaryResynthesizer] which can deserialize it. | |
| 1159 * | |
| 1160 * Caller is responsible for checking the library for errors, and adding any | |
| 1161 * dependent libraries using [addLibrary]. | |
| 1162 */ | |
| 1163 TestSummaryResynthesizer encodeLibraryElement(LibraryElementImpl library, | |
| 1164 {bool dumpSummaries: false}) { | |
| 1165 Map<String, UnlinkedUnit> unlinkedSummaries = <String, UnlinkedUnit>{}; | |
| 1166 LinkedLibrary getLinkedSummaryFor(LibraryElement lib) { | |
| 1167 LibrarySerializationResult serialized = serializeLibrary( | |
| 1168 lib, context.typeProvider, context.analysisOptions.strongMode); | |
| 1169 for (int i = 0; i < serialized.unlinkedUnits.length; i++) { | |
| 1170 unlinkedSummaries[serialized.unitUris[i]] = | |
| 1171 new UnlinkedUnit.fromBuffer(serialized.unlinkedUnits[i].toBuffer()); | |
| 1172 } | |
| 1173 return new LinkedLibrary.fromBuffer(serialized.linked.toBuffer()); | |
| 1174 } | |
| 1175 | |
| 1176 Map<String, LinkedLibrary> linkedSummaries = <String, LinkedLibrary>{ | |
| 1177 library.source.uri.toString(): getLinkedSummaryFor(library) | |
| 1178 }; | |
| 1179 for (Source source in otherLibrarySources) { | |
| 1180 LibraryElement original = context.computeLibraryElement(source); | |
| 1181 String uri = source.uri.toString(); | |
| 1182 linkedSummaries[uri] = getLinkedSummaryFor(original); | |
| 1183 } | |
| 1184 if (dumpSummaries) { | |
| 1185 unlinkedSummaries.forEach((String path, UnlinkedUnit unit) { | |
| 1186 print('Unlinked $path: ${JSON.encode(canonicalize(unit))}'); | |
| 1187 }); | |
| 1188 linkedSummaries.forEach((String path, LinkedLibrary lib) { | |
| 1189 print('Linked $path: ${JSON.encode(canonicalize(lib))}'); | |
| 1190 }); | |
| 1191 } | |
| 1192 return new TestSummaryResynthesizer( | |
| 1193 null, context, unlinkedSummaries, linkedSummaries, allowMissingFiles); | |
| 1194 } | |
| 1195 | |
| 1196 ElementImpl getActualElement(Element element, String desc) { | 1129 ElementImpl getActualElement(Element element, String desc) { |
| 1197 if (element == null) { | 1130 if (element == null) { |
| 1198 return null; | 1131 return null; |
| 1199 } else if (element is ElementImpl) { | 1132 } else if (element is ElementImpl) { |
| 1200 return element; | 1133 return element; |
| 1201 } else if (element is ElementHandle) { | 1134 } else if (element is ElementHandle) { |
| 1202 Element actualElement = element.actualElement; | 1135 Element actualElement = element.actualElement; |
| 1203 // A handle should never point to a member, because if it did, then | 1136 // A handle should never point to a member, because if it did, then |
| 1204 // "is Member" checks on the handle would produce the wrong result. | 1137 // "is Member" checks on the handle would produce the wrong result. |
| 1205 expect(actualElement, isNot(new isInstanceOf<Member>()), reason: desc); | 1138 expect(actualElement, isNot(new isInstanceOf<Member>()), reason: desc); |
| (...skipping 131 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1337 return false; | 1270 return false; |
| 1338 } else if (modifier == Modifier.SYNTHETIC) { | 1271 } else if (modifier == Modifier.SYNTHETIC) { |
| 1339 return element.isSynthetic; | 1272 return element.isSynthetic; |
| 1340 } | 1273 } |
| 1341 throw new UnimplementedError( | 1274 throw new UnimplementedError( |
| 1342 'Modifier $modifier for ${element?.runtimeType}'); | 1275 'Modifier $modifier for ${element?.runtimeType}'); |
| 1343 } | 1276 } |
| 1344 } | 1277 } |
| 1345 | 1278 |
| 1346 @reflectiveTest | 1279 @reflectiveTest |
| 1347 class ResynthesizeElementTest extends ResynthesizeTest { | |
| 1348 @override | |
| 1349 LibraryElementImpl checkLibrary(String text, | |
| 1350 {bool allowErrors: false, bool dumpSummaries: false}) { | |
| 1351 Source source = addTestSource(text); | |
| 1352 LibraryElementImpl original = context.computeLibraryElement(source); | |
| 1353 LibraryElementImpl resynthesized = resynthesizeLibraryElement( | |
| 1354 encodeLibrary(original, | |
| 1355 allowErrors: allowErrors, dumpSummaries: dumpSummaries), | |
| 1356 source.uri.toString(), | |
| 1357 original); | |
| 1358 checkLibraryElements(original, resynthesized); | |
| 1359 return resynthesized; | |
| 1360 } | |
| 1361 | |
| 1362 @override | |
| 1363 SummaryResynthesizer encodeDecodeLibrarySource(Source librarySource) { | |
| 1364 LibraryElement libraryElement = | |
| 1365 context.computeLibraryElement(librarySource); | |
| 1366 return encodeLibrary(libraryElement); | |
| 1367 } | |
| 1368 | |
| 1369 /** | |
| 1370 * Serialize the given [library] into a summary. Then create a | |
| 1371 * [TestSummaryResynthesizer] which can deserialize it, along with any | |
| 1372 * references it makes to `dart:core`. | |
| 1373 * | |
| 1374 * Errors will lead to a test failure unless [allowErrors] is `true`. | |
| 1375 */ | |
| 1376 TestSummaryResynthesizer encodeLibrary(LibraryElementImpl library, | |
| 1377 {bool allowErrors: false, bool dumpSummaries: false}) { | |
| 1378 if (!allowErrors) { | |
| 1379 assertNoErrors(library.source); | |
| 1380 } | |
| 1381 addLibrary('dart:core'); | |
| 1382 addLibrary('dart:async'); | |
| 1383 addLibrary('dart:math'); | |
| 1384 return encodeLibraryElement(library, dumpSummaries: dumpSummaries); | |
| 1385 } | |
| 1386 | |
| 1387 /** | |
| 1388 * Convert the library element [library] into a summary, and then create a | |
| 1389 * [TestSummaryResynthesizer] which can deserialize it. | |
| 1390 * | |
| 1391 * Caller is responsible for checking the library for errors, and adding any | |
| 1392 * dependent libraries using [addLibrary]. | |
| 1393 */ | |
| 1394 TestSummaryResynthesizer encodeLibraryElement(LibraryElementImpl library, | |
| 1395 {bool dumpSummaries: false}) { | |
| 1396 Map<String, UnlinkedUnit> unlinkedSummaries = <String, UnlinkedUnit>{}; | |
| 1397 LinkedLibrary getLinkedSummaryFor(LibraryElement lib) { | |
| 1398 LibrarySerializationResult serialized = serializeLibrary( | |
| 1399 lib, context.typeProvider, context.analysisOptions.strongMode); | |
| 1400 for (int i = 0; i < serialized.unlinkedUnits.length; i++) { | |
| 1401 unlinkedSummaries[serialized.unitUris[i]] = | |
| 1402 new UnlinkedUnit.fromBuffer(serialized.unlinkedUnits[i].toBuffer()); | |
| 1403 } | |
| 1404 return new LinkedLibrary.fromBuffer(serialized.linked.toBuffer()); | |
| 1405 } | |
| 1406 | |
| 1407 Map<String, LinkedLibrary> linkedSummaries = <String, LinkedLibrary>{ | |
| 1408 library.source.uri.toString(): getLinkedSummaryFor(library) | |
| 1409 }; | |
| 1410 for (Source source in otherLibrarySources) { | |
| 1411 LibraryElement original = context.computeLibraryElement(source); | |
| 1412 String uri = source.uri.toString(); | |
| 1413 linkedSummaries[uri] = getLinkedSummaryFor(original); | |
| 1414 } | |
| 1415 if (dumpSummaries) { | |
| 1416 unlinkedSummaries.forEach((String path, UnlinkedUnit unit) { | |
| 1417 print('Unlinked $path: ${JSON.encode(canonicalize(unit))}'); | |
| 1418 }); | |
| 1419 linkedSummaries.forEach((String path, LinkedLibrary lib) { | |
| 1420 print('Linked $path: ${JSON.encode(canonicalize(lib))}'); | |
| 1421 }); | |
| 1422 } | |
| 1423 return new TestSummaryResynthesizer( | |
| 1424 null, context, unlinkedSummaries, linkedSummaries, allowMissingFiles); | |
| 1425 } | |
| 1426 | |
| 1427 /** | |
| 1428 * Resynthesize the library element associated with [uri] using | |
| 1429 * [resynthesizer], and verify that it only had to consult one summary in | |
| 1430 * order to do so. [original] is consulted merely to verify that no | |
| 1431 * unnecessary resynthesis work was performed. | |
| 1432 */ | |
| 1433 LibraryElementImpl resynthesizeLibraryElement( | |
| 1434 TestSummaryResynthesizer resynthesizer, | |
| 1435 String uri, | |
| 1436 LibraryElement original) { | |
| 1437 LibraryElementImpl resynthesized = resynthesizer.getLibraryElement(uri); | |
| 1438 checkMinimalResynthesisWork(resynthesizer, original); | |
| 1439 return resynthesized; | |
| 1440 } | |
| 1441 | |
| 1442 test_core() { | |
| 1443 addLibrary('dart:async'); | |
| 1444 addLibrary('dart:math'); | |
| 1445 String uri = 'dart:core'; | |
| 1446 LibraryElementImpl original = | |
| 1447 context.computeLibraryElement(context.sourceFactory.forUri(uri)); | |
| 1448 LibraryElementImpl resynthesized = resynthesizeLibraryElement( | |
| 1449 encodeLibraryElement(original), uri, original); | |
| 1450 checkLibraryElements(original, resynthesized); | |
| 1451 } | |
| 1452 } | |
| 1453 | |
| 1454 @reflectiveTest | |
| 1455 abstract class ResynthesizeTest extends AbstractResynthesizeTest { | 1280 abstract class ResynthesizeTest extends AbstractResynthesizeTest { |
| 1456 LibraryElementImpl checkLibrary(String text, | 1281 LibraryElementImpl checkLibrary(String text, |
| 1457 {bool allowErrors: false, bool dumpSummaries: false}); | 1282 {bool allowErrors: false, bool dumpSummaries: false}); |
| 1458 | 1283 |
| 1459 /** | 1284 /** |
| 1460 * Return a [SummaryResynthesizer] to resynthesize the library with the | 1285 * Return a [SummaryResynthesizer] to resynthesize the library with the |
| 1461 * given [librarySource]. | 1286 * given [librarySource]. |
| 1462 */ | 1287 */ |
| 1463 SummaryResynthesizer encodeDecodeLibrarySource(Source librarySource); | 1288 SummaryResynthesizer encodeDecodeLibrarySource(Source librarySource); |
| 1464 | 1289 |
| (...skipping 3335 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 4800 fail('Unexpectedly tried to get unlinked summary for $uri'); | 4625 fail('Unexpectedly tried to get unlinked summary for $uri'); |
| 4801 } | 4626 } |
| 4802 return serializedUnit; | 4627 return serializedUnit; |
| 4803 } | 4628 } |
| 4804 | 4629 |
| 4805 @override | 4630 @override |
| 4806 bool hasLibrarySummary(String uri) { | 4631 bool hasLibrarySummary(String uri) { |
| 4807 return true; | 4632 return true; |
| 4808 } | 4633 } |
| 4809 } | 4634 } |
| OLD | NEW |