OLD | NEW |
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 test.analysis.notification.navigation; | 5 library test.analysis.notification.navigation; |
6 | 6 |
7 import 'dart:async'; | 7 import 'dart:async'; |
8 | 8 |
9 import 'package:analysis_server/src/constants.dart'; | 9 import 'package:analysis_server/src/constants.dart'; |
10 import 'package:analysis_server/src/protocol.dart'; | 10 import 'package:analysis_server/src/protocol.dart'; |
11 import 'package:test_reflective_loader/test_reflective_loader.dart'; | 11 import 'package:test_reflective_loader/test_reflective_loader.dart'; |
12 import 'package:unittest/unittest.dart'; | 12 import 'package:unittest/unittest.dart'; |
13 | 13 |
14 import '../analysis_abstract.dart'; | 14 import '../analysis_abstract.dart'; |
15 | 15 |
16 main() { | 16 main() { |
17 groupSep = ' | '; | 17 groupSep = ' | '; |
18 defineReflectiveTests(AnalysisNotificationNavigationTest); | 18 defineReflectiveTests(AnalysisNotificationNavigationTest); |
19 } | 19 } |
20 | 20 |
21 @reflectiveTest | 21 @reflectiveTest |
22 class AnalysisNotificationNavigationTest extends AbstractAnalysisTest { | 22 class AnalysisNotificationNavigationTest extends AbstractNavigationTest { |
23 List<NavigationRegion> regions; | |
24 List<NavigationTarget> targets; | |
25 List<String> targetFiles; | |
26 | |
27 NavigationRegion testRegion; | |
28 List<int> testTargetIndexes; | |
29 NavigationTarget testTarget; | |
30 | |
31 /** | |
32 * Validates that there is a target in [testTargetIndexes] with [file], | |
33 * at [offset] and with the given [length]. | |
34 */ | |
35 void assertHasFileTarget(String file, int offset, int length) { | |
36 List<NavigationTarget> testTargets = | |
37 testTargetIndexes.map((int index) => targets[index]).toList(); | |
38 for (NavigationTarget target in testTargets) { | |
39 if (targetFiles[target.fileIndex] == file && | |
40 target.offset == offset && | |
41 target.length == length) { | |
42 testTarget = target; | |
43 return; | |
44 } | |
45 } | |
46 fail( | |
47 'Expected to find target (file=$file; offset=$offset; length=$length) in
\n' | |
48 '${testRegion} in\n' '${testTargets.join('\n')}'); | |
49 } | |
50 | |
51 void assertHasOperatorRegion(String regionSearch, int regionLength, | |
52 String targetSearch, int targetLength) { | |
53 assertHasRegion(regionSearch, regionLength); | |
54 assertHasTarget(targetSearch, targetLength); | |
55 } | |
56 | |
57 /** | |
58 * Validates that there is a region at the offset of [search] in [testFile]. | |
59 * If [length] is not specified explicitly, then length of an identifier | |
60 * from [search] is used. | |
61 */ | |
62 void assertHasRegion(String search, [int length = -1]) { | |
63 int offset = findOffset(search); | |
64 if (length == -1) { | |
65 length = findIdentifierLength(search); | |
66 } | |
67 findRegion(offset, length, true); | |
68 } | |
69 | |
70 /** | |
71 * Validates that there is a region at the offset of [search] in [testFile] | |
72 * with the given [length] or the length of [search]. | |
73 */ | |
74 void assertHasRegionString(String search, [int length = -1]) { | |
75 int offset = findOffset(search); | |
76 if (length == -1) { | |
77 length = search.length; | |
78 } | |
79 findRegion(offset, length, true); | |
80 } | |
81 | |
82 /** | |
83 * Validates that there is an identifier region at [regionSearch] with target | |
84 * at [targetSearch]. | |
85 */ | |
86 void assertHasRegionTarget(String regionSearch, String targetSearch) { | |
87 assertHasRegion(regionSearch); | |
88 assertHasTarget(targetSearch); | |
89 } | |
90 | |
91 /** | |
92 * Validates that there is a target in [testTargets] with [testFile], at the | |
93 * offset of [search] in [testFile], and with the given [length] or the length | |
94 * of an leading identifier in [search]. | |
95 */ | |
96 void assertHasTarget(String search, [int length = -1]) { | |
97 int offset = findOffset(search); | |
98 if (length == -1) { | |
99 length = findIdentifierLength(search); | |
100 } | |
101 assertHasFileTarget(testFile, offset, length); | |
102 } | |
103 | |
104 /** | |
105 * Validates that there is no a region at [search] and with the given | |
106 * [length]. | |
107 */ | |
108 void assertNoRegion(String search, int length) { | |
109 int offset = findOffset(search); | |
110 findRegion(offset, length, false); | |
111 } | |
112 | |
113 /** | |
114 * Validates that there is no a region at [search] with any length. | |
115 */ | |
116 void assertNoRegionAt(String search) { | |
117 int offset = findOffset(search); | |
118 findRegion(offset, -1, false); | |
119 } | |
120 | |
121 /** | |
122 * Validates that there is no a region for [search] string. | |
123 */ | |
124 void assertNoRegionString(String search) { | |
125 int offset = findOffset(search); | |
126 int length = search.length; | |
127 findRegion(offset, length, false); | |
128 } | |
129 | |
130 void assertRegionsSorted() { | |
131 int lastEnd = -1; | |
132 for (NavigationRegion region in regions) { | |
133 int offset = region.offset; | |
134 if (offset < lastEnd) { | |
135 fail('$lastEnd was expected to be > $offset in\n' + regions.join('\n')); | |
136 } | |
137 lastEnd = offset + region.length; | |
138 } | |
139 } | |
140 | |
141 /** | |
142 * Finds the navigation region with the given [offset] and [length]. | |
143 * If [length] is `-1`, then it is ignored. | |
144 * | |
145 * If [exists] is `true`, then fails if such region does not exist. | |
146 * Otherwise remembers this it into [testRegion]. | |
147 * Also fills [testTargets] with its targets. | |
148 * | |
149 * If [exists] is `false`, then fails if such region exists. | |
150 */ | |
151 void findRegion(int offset, int length, bool exists) { | |
152 for (NavigationRegion region in regions) { | |
153 if (region.offset == offset && | |
154 (length == -1 || region.length == length)) { | |
155 if (exists == false) { | |
156 fail('Not expected to find (offset=$offset; length=$length) in\n' | |
157 '${regions.join('\n')}'); | |
158 } | |
159 testRegion = region; | |
160 testTargetIndexes = region.targets; | |
161 return; | |
162 } | |
163 } | |
164 if (exists == true) { | |
165 fail('Expected to find (offset=$offset; length=$length) in\n' | |
166 '${regions.join('\n')}'); | |
167 } | |
168 } | |
169 | |
170 Future prepareNavigation() { | 23 Future prepareNavigation() { |
171 addAnalysisSubscription(AnalysisService.NAVIGATION, testFile); | 24 addAnalysisSubscription(AnalysisService.NAVIGATION, testFile); |
172 return waitForTasksFinished().then((_) { | 25 return waitForTasksFinished().then((_) { |
173 assertRegionsSorted(); | 26 assertRegionsSorted(); |
174 }); | 27 }); |
175 } | 28 } |
176 | 29 |
177 void processNotification(Notification notification) { | 30 void processNotification(Notification notification) { |
178 if (notification.event == ANALYSIS_NAVIGATION) { | 31 if (notification.event == ANALYSIS_NAVIGATION) { |
179 var params = new AnalysisNavigationParams.fromNotification(notification); | 32 var params = new AnalysisNavigationParams.fromNotification(notification); |
(...skipping 598 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
778 test_type_void() { | 631 test_type_void() { |
779 addTestFile(''' | 632 addTestFile(''' |
780 void main() { | 633 void main() { |
781 } | 634 } |
782 '''); | 635 '''); |
783 return prepareNavigation().then((_) { | 636 return prepareNavigation().then((_) { |
784 assertNoRegionAt('void'); | 637 assertNoRegionAt('void'); |
785 }); | 638 }); |
786 } | 639 } |
787 } | 640 } |
| 641 |
| 642 class AbstractNavigationTest extends AbstractAnalysisTest { |
| 643 List<NavigationRegion> regions; |
| 644 List<NavigationTarget> targets; |
| 645 List<String> targetFiles; |
| 646 |
| 647 NavigationRegion testRegion; |
| 648 List<int> testTargetIndexes; |
| 649 NavigationTarget testTarget; |
| 650 |
| 651 /** |
| 652 * Validates that there is a target in [testTargetIndexes] with [file], |
| 653 * at [offset] and with the given [length]. |
| 654 */ |
| 655 void assertHasFileTarget(String file, int offset, int length) { |
| 656 List<NavigationTarget> testTargets = |
| 657 testTargetIndexes.map((int index) => targets[index]).toList(); |
| 658 for (NavigationTarget target in testTargets) { |
| 659 if (targetFiles[target.fileIndex] == file && |
| 660 target.offset == offset && |
| 661 target.length == length) { |
| 662 testTarget = target; |
| 663 return; |
| 664 } |
| 665 } |
| 666 fail( |
| 667 'Expected to find target (file=$file; offset=$offset; length=$length) in
\n' |
| 668 '${testRegion} in\n' '${testTargets.join('\n')}'); |
| 669 } |
| 670 |
| 671 void assertHasOperatorRegion(String regionSearch, int regionLength, |
| 672 String targetSearch, int targetLength) { |
| 673 assertHasRegion(regionSearch, regionLength); |
| 674 assertHasTarget(targetSearch, targetLength); |
| 675 } |
| 676 |
| 677 /** |
| 678 * Validates that there is a region at the offset of [search] in [testFile]. |
| 679 * If [length] is not specified explicitly, then length of an identifier |
| 680 * from [search] is used. |
| 681 */ |
| 682 void assertHasRegion(String search, [int length = -1]) { |
| 683 int offset = findOffset(search); |
| 684 if (length == -1) { |
| 685 length = findIdentifierLength(search); |
| 686 } |
| 687 findRegion(offset, length, true); |
| 688 } |
| 689 |
| 690 /** |
| 691 * Validates that there is a region at the offset of [search] in [testFile] |
| 692 * with the given [length] or the length of [search]. |
| 693 */ |
| 694 void assertHasRegionString(String search, [int length = -1]) { |
| 695 int offset = findOffset(search); |
| 696 if (length == -1) { |
| 697 length = search.length; |
| 698 } |
| 699 findRegion(offset, length, true); |
| 700 } |
| 701 |
| 702 /** |
| 703 * Validates that there is an identifier region at [regionSearch] with target |
| 704 * at [targetSearch]. |
| 705 */ |
| 706 void assertHasRegionTarget(String regionSearch, String targetSearch) { |
| 707 assertHasRegion(regionSearch); |
| 708 assertHasTarget(targetSearch); |
| 709 } |
| 710 |
| 711 /** |
| 712 * Validates that there is a target in [testTargets] with [testFile], at the |
| 713 * offset of [search] in [testFile], and with the given [length] or the length |
| 714 * of an leading identifier in [search]. |
| 715 */ |
| 716 void assertHasTarget(String search, [int length = -1]) { |
| 717 int offset = findOffset(search); |
| 718 if (length == -1) { |
| 719 length = findIdentifierLength(search); |
| 720 } |
| 721 assertHasFileTarget(testFile, offset, length); |
| 722 } |
| 723 |
| 724 /** |
| 725 * Validates that there is no a region at [search] and with the given |
| 726 * [length]. |
| 727 */ |
| 728 void assertNoRegion(String search, int length) { |
| 729 int offset = findOffset(search); |
| 730 findRegion(offset, length, false); |
| 731 } |
| 732 |
| 733 /** |
| 734 * Validates that there is no a region at [search] with any length. |
| 735 */ |
| 736 void assertNoRegionAt(String search) { |
| 737 int offset = findOffset(search); |
| 738 findRegion(offset, -1, false); |
| 739 } |
| 740 |
| 741 /** |
| 742 * Validates that there is no a region for [search] string. |
| 743 */ |
| 744 void assertNoRegionString(String search) { |
| 745 int offset = findOffset(search); |
| 746 int length = search.length; |
| 747 findRegion(offset, length, false); |
| 748 } |
| 749 |
| 750 void assertRegionsSorted() { |
| 751 int lastEnd = -1; |
| 752 for (NavigationRegion region in regions) { |
| 753 int offset = region.offset; |
| 754 if (offset < lastEnd) { |
| 755 fail('$lastEnd was expected to be > $offset in\n' + regions.join('\n')); |
| 756 } |
| 757 lastEnd = offset + region.length; |
| 758 } |
| 759 } |
| 760 |
| 761 /** |
| 762 * Finds the navigation region with the given [offset] and [length]. |
| 763 * If [length] is `-1`, then it is ignored. |
| 764 * |
| 765 * If [exists] is `true`, then fails if such region does not exist. |
| 766 * Otherwise remembers this it into [testRegion]. |
| 767 * Also fills [testTargets] with its targets. |
| 768 * |
| 769 * If [exists] is `false`, then fails if such region exists. |
| 770 */ |
| 771 void findRegion(int offset, int length, bool exists) { |
| 772 for (NavigationRegion region in regions) { |
| 773 if (region.offset == offset && |
| 774 (length == -1 || region.length == length)) { |
| 775 if (exists == false) { |
| 776 fail('Not expected to find (offset=$offset; length=$length) in\n' |
| 777 '${regions.join('\n')}'); |
| 778 } |
| 779 testRegion = region; |
| 780 testTargetIndexes = region.targets; |
| 781 return; |
| 782 } |
| 783 } |
| 784 if (exists == true) { |
| 785 fail('Expected to find (offset=$offset; length=$length) in\n' |
| 786 '${regions.join('\n')}'); |
| 787 } |
| 788 } |
| 789 } |
OLD | NEW |