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

Side by Side Diff: pkg/analyzer/lib/src/generated/incremental_resolution_validator.dart

Issue 839913002: Validate incremental resolutions results if requested. (Closed) Base URL: https://dart.googlecode.com/svn/branches/bleeding_edge/dart
Patch Set: Created 5 years, 11 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch | Annotate | Revision Log
OLDNEW
1 // Copyright (c) 2014, the Dart project authors. Please see the AUTHORS file 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 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 engine.incremental_resolution_validator; 5 library engine.incremental_resolution_validator;
6 6
7 import 'package:analyzer/src/generated/ast.dart'; 7 import 'package:analyzer/src/generated/ast.dart';
8 import 'package:analyzer/src/generated/element.dart'; 8 import 'package:analyzer/src/generated/element.dart';
9 9
10 10
11 /**
12 * Validates that the [actual] and the [expected] units have the same structure
13 * and resolution. Throws [IncrementalResolutionMismatch] otherwise.
14 */
11 void assertSameResolution(CompilationUnit actual, CompilationUnit expected, 15 void assertSameResolution(CompilationUnit actual, CompilationUnit expected,
12 FailHandler failHandler) { 16 {bool validateTypes: false}) {
danrubel 2015/01/07 22:32:48 validateTypes true by default?
13 _SameResolutionValidator validator = 17 _SameResolutionValidator validator =
14 new _SameResolutionValidator(failHandler, expected); 18 new _SameResolutionValidator(validateTypes, expected);
15 actual.accept(validator); 19 actual.accept(validator);
16 } 20 }
17 21
18 22
19 typedef FailHandler(String reason); 23 /**
24 * This exception is thrown when a mismatch between actual and expected AST
25 * or resolution is found.
26 */
27 class IncrementalResolutionMismatch {
28 final String message;
29 IncrementalResolutionMismatch(this.message);
30 }
20 31
21 32
22 class _SameResolutionValidator implements AstVisitor { 33 class _SameResolutionValidator implements AstVisitor {
23 final FailHandler failHandler; 34 final bool validateTypes;
24 AstNode other; 35 AstNode other;
25 36
26 _SameResolutionValidator(this.failHandler, this.other); 37 _SameResolutionValidator(this.validateTypes, this.other);
27 38
28 @override 39 @override
29 visitAdjacentStrings(AdjacentStrings node) { 40 visitAdjacentStrings(AdjacentStrings node) {
30 } 41 }
31 42
32 @override 43 @override
33 visitAnnotation(Annotation node) { 44 visitAnnotation(Annotation node) {
34 Annotation other = this.other; 45 Annotation other = this.other;
35 _visitNode(node.name, other.name); 46 _visitNode(node.name, other.name);
36 _visitNode(node.constructorName, other.constructorName); 47 _visitNode(node.constructorName, other.constructorName);
(...skipping 731 matching lines...) Expand 10 before | Expand all | Expand 10 after
768 visitYieldStatement(YieldStatement node) { 779 visitYieldStatement(YieldStatement node) {
769 YieldStatement other = this.other; 780 YieldStatement other = this.other;
770 _visitNode(node.expression, other.expression); 781 _visitNode(node.expression, other.expression);
771 } 782 }
772 783
773 void _expectEquals(actual, expected) { 784 void _expectEquals(actual, expected) {
774 if (actual != expected) { 785 if (actual != expected) {
775 String message = ''; 786 String message = '';
776 message += 'Expected: $expected\n'; 787 message += 'Expected: $expected\n';
777 message += ' Actual: $actual\n'; 788 message += ' Actual: $actual\n';
778 failHandler(message); 789 _fail(message);
779 } 790 }
780 } 791 }
781 792
782 void _expectIsNull(obj) { 793 void _expectIsNull(obj) {
783 if (obj != null) { 794 if (obj != null) {
784 String message = ''; 795 String message = '';
785 message += 'Expected: null\n'; 796 message += 'Expected: null\n';
786 message += ' Actual: $obj\n'; 797 message += ' Actual: $obj\n';
787 failHandler(message); 798 _fail(message);
788 } 799 }
789 } 800 }
790 801
791 void _expectLength(List actualList, int expected) { 802 void _expectLength(List actualList, int expected) {
792 String message = ''; 803 String message = '';
793 message += 'Expected length: $expected\n'; 804 message += 'Expected length: $expected\n';
794 if (actualList == null) { 805 if (actualList == null) {
795 message += 'but null found.'; 806 message += 'but null found.';
796 failHandler(message); 807 _fail(message);
797 } 808 }
798 int actual = actualList.length; 809 int actual = actualList.length;
799 if (actual != expected) { 810 if (actual != expected) {
800 message += 'but $actual found\n'; 811 message += 'but $actual found\n';
801 message += 'in $actualList'; 812 message += 'in $actualList';
802 failHandler(message); 813 _fail(message);
803 } 814 }
804 } 815 }
805 816
817 void _fail(String message) {
818 throw new IncrementalResolutionMismatch(message);
819 }
820
806 void _verifyElement(Element a, Element b) { 821 void _verifyElement(Element a, Element b) {
807 if (a != b) { 822 if (a is Member && b is Member) {
808 print(a.location); 823 a = (a as Member).baseElement;
809 print(b.location); 824 b = (b as Member).baseElement;
810 failHandler('Expected: $b\n Actual: $a'); 825 }
826 String locationA = _getElementLocationWithoutUri(a);
827 String locationB = _getElementLocationWithoutUri(b);
828 if (locationA != locationB) {
829 int offset = other.offset;
830 _fail('[$offset]\nExpected: $b ($locationB)\n Actual: $a ($locationA)');
811 } 831 }
812 if (a == null && b == null) { 832 if (a == null && b == null) {
813 return; 833 return;
814 } 834 }
815 if (a.nameOffset != b.nameOffset) { 835 if (a.nameOffset != b.nameOffset) {
816 failHandler('Expected: ${b.nameOffset}\n Actual: ${a.nameOffset}'); 836 _fail('Expected: ${b.nameOffset}\n Actual: ${a.nameOffset}');
817 } 837 }
818 } 838 }
819 839
820 void _verifyType(DartType a, DartType b) { 840 void _verifyType(DartType a, DartType b) {
841 if (!validateTypes) {
842 return;
843 }
821 if (a != b) { 844 if (a != b) {
822 failHandler('Expected: $b\n Actual: $a'); 845 int offset = other.offset;
846 _fail('[$offset]\nExpected: $b\n Actual: $a');
823 } 847 }
824 } 848 }
825 849
826 void _visitAnnotatedNode(AnnotatedNode node, AnnotatedNode other) { 850 void _visitAnnotatedNode(AnnotatedNode node, AnnotatedNode other) {
827 _visitNode(node.documentationComment, other.documentationComment); 851 _visitNode(node.documentationComment, other.documentationComment);
828 _visitList(node.metadata, other.metadata); 852 _visitList(node.metadata, other.metadata);
829 } 853 }
830 854
831 _visitDeclaration(Declaration node, Declaration other) { 855 _visitDeclaration(Declaration node, Declaration other) {
832 _verifyElement(node.element, other.element); 856 _verifyElement(node.element, other.element);
(...skipping 31 matching lines...) Expand 10 before | Expand all | Expand 10 after
864 } 888 }
865 } 889 }
866 890
867 void _visitNormalFormalParameter(NormalFormalParameter node, 891 void _visitNormalFormalParameter(NormalFormalParameter node,
868 NormalFormalParameter other) { 892 NormalFormalParameter other) {
869 _verifyElement(node.element, other.element); 893 _verifyElement(node.element, other.element);
870 _visitNode(node.documentationComment, other.documentationComment); 894 _visitNode(node.documentationComment, other.documentationComment);
871 _visitList(node.metadata, other.metadata); 895 _visitList(node.metadata, other.metadata);
872 _visitNode(node.identifier, other.identifier); 896 _visitNode(node.identifier, other.identifier);
873 } 897 }
898
899 /**
900 * Returns an URI scheme independent version of the [element] location.
901 */
902 static String _getElementLocationWithoutUri(Element element) {
903 if (element == null) {
904 return '<null>';
905 }
906 if (element is UriReferencedElementImpl) {
907 return '<ignored>';
908 }
909 ElementLocation location = element.location;
910 List<String> components = location.components;
911 String uriPrefix = '';
912 Element unit = element is CompilationUnitElement ?
913 element :
914 element.getAncestor((e) => e is CompilationUnitElement);
915 if (unit != null) {
916 String libComponent = components[0];
917 String unitComponent = components[1];
918 components = components.sublist(2);
919 uriPrefix = _getShortElementLocationUri(libComponent) +
920 ':' +
921 _getShortElementLocationUri(unitComponent);
922 } else {
923 String libComponent = components[0];
924 components = components.sublist(1);
925 uriPrefix = _getShortElementLocationUri(libComponent);
926 }
927 return uriPrefix + ':' + components.join(':');
928 }
929
930 /**
931 * Returns a "short" version of the given [uri].
932 *
933 * For example:
934 * /User/me/project/lib/my_lib.dart -> my_lib.dart
935 * package:project/my_lib.dart -> my_lib.dart
936 */
937 static String _getShortElementLocationUri(String uri) {
938 int index = uri.lastIndexOf('/');
939 if (index == -1) {
940 return uri;
941 }
942 return uri.substring(index + 1);
943 }
874 } 944 }
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698