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.services.completion.dart.keyword; | 5 library test.services.completion.dart.keyword; |
6 | 6 |
7 import 'package:analysis_server/src/protocol.dart'; | 7 import 'package:analysis_server/src/protocol.dart'; |
8 import 'package:analysis_server/src/services/completion/dart_completion_manager.
dart'; | 8 import 'package:analysis_server/src/services/completion/dart_completion_manager.
dart'; |
9 import 'package:analysis_server/src/services/completion/keyword_contributor.dart
'; | 9 import 'package:analysis_server/src/services/completion/keyword_contributor.dart
'; |
10 import 'package:analyzer/src/generated/scanner.dart'; | 10 import 'package:analyzer/src/generated/scanner.dart'; |
(...skipping 61 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
72 Keyword.PART, | 72 Keyword.PART, |
73 Keyword.TYPEDEF, | 73 Keyword.TYPEDEF, |
74 Keyword.VAR, | 74 Keyword.VAR, |
75 Keyword.VOID | 75 Keyword.VOID |
76 ]; | 76 ]; |
77 | 77 |
78 static const List<String> NO_PSEUDO_KEYWORDS = const []; | 78 static const List<String> NO_PSEUDO_KEYWORDS = const []; |
79 | 79 |
80 static const List<Keyword> STMT_START_IN_CLASS = const [ | 80 static const List<Keyword> STMT_START_IN_CLASS = const [ |
81 Keyword.ASSERT, | 81 Keyword.ASSERT, |
| 82 Keyword.CONST, |
| 83 Keyword.DO, |
| 84 Keyword.FINAL, |
| 85 Keyword.FOR, |
| 86 Keyword.IF, |
| 87 Keyword.NEW, |
| 88 Keyword.RETHROW, |
| 89 Keyword.RETURN, |
| 90 Keyword.SUPER, |
| 91 Keyword.SWITCH, |
| 92 Keyword.THIS, |
| 93 Keyword.THROW, |
| 94 Keyword.TRY, |
| 95 Keyword.VAR, |
| 96 Keyword.VOID, |
| 97 Keyword.WHILE |
| 98 ]; |
| 99 |
| 100 static const List<Keyword> STMT_START_IN_LOOP_IN_CLASS = const [ |
| 101 Keyword.ASSERT, |
| 102 Keyword.BREAK, |
| 103 Keyword.CONST, |
82 Keyword.CONTINUE, | 104 Keyword.CONTINUE, |
83 Keyword.DO, | 105 Keyword.DO, |
84 Keyword.FINAL, | 106 Keyword.FINAL, |
85 Keyword.FOR, | 107 Keyword.FOR, |
86 Keyword.IF, | 108 Keyword.IF, |
87 Keyword.NEW, | 109 Keyword.NEW, |
88 Keyword.RETHROW, | 110 Keyword.RETHROW, |
89 Keyword.RETURN, | 111 Keyword.RETURN, |
90 Keyword.SUPER, | 112 Keyword.SUPER, |
91 Keyword.SWITCH, | 113 Keyword.SWITCH, |
92 Keyword.THIS, | 114 Keyword.THIS, |
93 Keyword.THROW, | 115 Keyword.THROW, |
94 Keyword.TRY, | 116 Keyword.TRY, |
95 Keyword.VAR, | 117 Keyword.VAR, |
96 Keyword.VOID, | 118 Keyword.VOID, |
97 Keyword.WHILE | 119 Keyword.WHILE |
98 ]; | 120 ]; |
99 | 121 |
100 static const List<Keyword> STMT_START_IN_SWITCH_IN_CLASS = const [ | 122 static const List<Keyword> STMT_START_IN_SWITCH_IN_CLASS = const [ |
101 Keyword.ASSERT, | 123 Keyword.ASSERT, |
| 124 Keyword.BREAK, |
102 Keyword.CASE, | 125 Keyword.CASE, |
103 Keyword.CONTINUE, | 126 Keyword.CONST, |
104 Keyword.DEFAULT, | 127 Keyword.DEFAULT, |
105 Keyword.DO, | 128 Keyword.DO, |
106 Keyword.FINAL, | 129 Keyword.FINAL, |
107 Keyword.FOR, | 130 Keyword.FOR, |
108 Keyword.IF, | 131 Keyword.IF, |
109 Keyword.NEW, | 132 Keyword.NEW, |
110 Keyword.RETHROW, | 133 Keyword.RETHROW, |
111 Keyword.RETURN, | 134 Keyword.RETURN, |
112 Keyword.SUPER, | 135 Keyword.SUPER, |
113 Keyword.SWITCH, | 136 Keyword.SWITCH, |
114 Keyword.THIS, | 137 Keyword.THIS, |
115 Keyword.THROW, | 138 Keyword.THROW, |
116 Keyword.TRY, | 139 Keyword.TRY, |
117 Keyword.VAR, | 140 Keyword.VAR, |
118 Keyword.VOID, | 141 Keyword.VOID, |
119 Keyword.WHILE | 142 Keyword.WHILE |
120 ]; | 143 ]; |
121 | 144 |
122 static const List<Keyword> STMT_START_IN_SWITCH_OUTSIDE_CLASS = const [ | 145 static const List<Keyword> STMT_START_IN_SWITCH_OUTSIDE_CLASS = const [ |
123 Keyword.ASSERT, | 146 Keyword.ASSERT, |
| 147 Keyword.BREAK, |
124 Keyword.CASE, | 148 Keyword.CASE, |
125 Keyword.CONTINUE, | 149 Keyword.CONST, |
126 Keyword.DEFAULT, | 150 Keyword.DEFAULT, |
127 Keyword.DO, | 151 Keyword.DO, |
128 Keyword.FINAL, | 152 Keyword.FINAL, |
129 Keyword.FOR, | 153 Keyword.FOR, |
130 Keyword.IF, | 154 Keyword.IF, |
131 Keyword.NEW, | 155 Keyword.NEW, |
132 Keyword.RETHROW, | 156 Keyword.RETHROW, |
133 Keyword.RETURN, | 157 Keyword.RETURN, |
134 Keyword.SWITCH, | 158 Keyword.SWITCH, |
135 Keyword.THROW, | 159 Keyword.THROW, |
136 Keyword.TRY, | 160 Keyword.TRY, |
137 Keyword.VAR, | 161 Keyword.VAR, |
138 Keyword.VOID, | 162 Keyword.VOID, |
139 Keyword.WHILE | 163 Keyword.WHILE |
140 ]; | 164 ]; |
141 | 165 |
142 static const List<Keyword> STMT_START_OUTSIDE_CLASS = const [ | 166 static const List<Keyword> STMT_START_OUTSIDE_CLASS = const [ |
143 Keyword.ASSERT, | 167 Keyword.ASSERT, |
| 168 Keyword.CONST, |
| 169 Keyword.DO, |
| 170 Keyword.FINAL, |
| 171 Keyword.FOR, |
| 172 Keyword.IF, |
| 173 Keyword.NEW, |
| 174 Keyword.RETHROW, |
| 175 Keyword.RETURN, |
| 176 Keyword.SWITCH, |
| 177 Keyword.THROW, |
| 178 Keyword.TRY, |
| 179 Keyword.VAR, |
| 180 Keyword.VOID, |
| 181 Keyword.WHILE |
| 182 ]; |
| 183 |
| 184 static const List<Keyword> STMT_START_IN_LOOP_OUTSIDE_CLASS = const [ |
| 185 Keyword.ASSERT, |
| 186 Keyword.BREAK, |
| 187 Keyword.CONST, |
144 Keyword.CONTINUE, | 188 Keyword.CONTINUE, |
145 Keyword.DO, | 189 Keyword.DO, |
146 Keyword.FINAL, | 190 Keyword.FINAL, |
147 Keyword.FOR, | 191 Keyword.FOR, |
148 Keyword.IF, | 192 Keyword.IF, |
149 Keyword.NEW, | 193 Keyword.NEW, |
150 Keyword.RETHROW, | 194 Keyword.RETHROW, |
151 Keyword.RETURN, | 195 Keyword.RETURN, |
152 Keyword.SWITCH, | 196 Keyword.SWITCH, |
153 Keyword.THROW, | 197 Keyword.THROW, |
154 Keyword.TRY, | 198 Keyword.TRY, |
155 Keyword.VAR, | 199 Keyword.VAR, |
156 Keyword.VOID, | 200 Keyword.VOID, |
157 Keyword.WHILE | 201 Keyword.WHILE |
158 ]; | 202 ]; |
159 | 203 |
160 static const List<Keyword> EXPRESSION_START_INSTANCE = const [ | 204 static const List<Keyword> EXPRESSION_START_INSTANCE = const [ |
| 205 Keyword.CONST, |
161 Keyword.FALSE, | 206 Keyword.FALSE, |
162 Keyword.NEW, | 207 Keyword.NEW, |
163 Keyword.NULL, | 208 Keyword.NULL, |
164 Keyword.SUPER, | 209 Keyword.SUPER, |
165 Keyword.THIS, | 210 Keyword.THIS, |
166 Keyword.TRUE, | 211 Keyword.TRUE, |
167 ]; | 212 ]; |
168 | 213 |
169 static const List<Keyword> EXPRESSION_START_NO_INSTANCE = const [ | 214 static const List<Keyword> EXPRESSION_START_NO_INSTANCE = const [ |
| 215 Keyword.CONST, |
170 Keyword.FALSE, | 216 Keyword.FALSE, |
171 Keyword.NEW, | 217 Keyword.NEW, |
172 Keyword.NULL, | 218 Keyword.NULL, |
173 Keyword.TRUE, | 219 Keyword.TRUE, |
174 ]; | 220 ]; |
175 | 221 |
176 void assertSuggestKeywords(Iterable<Keyword> expectedKeywords, | 222 void assertSuggestKeywords(Iterable<Keyword> expectedKeywords, |
177 {List<String> pseudoKeywords: NO_PSEUDO_KEYWORDS, | 223 {List<String> pseudoKeywords: NO_PSEUDO_KEYWORDS, |
178 int relevance: DART_RELEVANCE_KEYWORD}) { | 224 int relevance: DART_RELEVANCE_KEYWORD}) { |
179 Set<String> expectedCompletions = new Set<String>(); | 225 Set<String> expectedCompletions = new Set<String>(); |
(...skipping 352 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
532 expect(computeFast(), isTrue); | 578 expect(computeFast(), isTrue); |
533 assertSuggestKeywords([Keyword.THIS]); | 579 assertSuggestKeywords([Keyword.THIS]); |
534 } | 580 } |
535 | 581 |
536 test_constructor_param2() { | 582 test_constructor_param2() { |
537 addTestSource('class A { A(t^) {});}'); | 583 addTestSource('class A { A(t^) {});}'); |
538 expect(computeFast(), isTrue); | 584 expect(computeFast(), isTrue); |
539 assertSuggestKeywords([Keyword.THIS]); | 585 assertSuggestKeywords([Keyword.THIS]); |
540 } | 586 } |
541 | 587 |
| 588 test_do_break_continue() { |
| 589 addTestSource('main() {do {^} while (true);}'); |
| 590 expect(computeFast(), isTrue); |
| 591 assertSuggestKeywords(STMT_START_IN_LOOP_OUTSIDE_CLASS, |
| 592 relevance: DART_RELEVANCE_KEYWORD); |
| 593 } |
| 594 |
| 595 test_do_break_continue2() { |
| 596 addTestSource('class A {foo() {do {^} while (true);}}'); |
| 597 expect(computeFast(), isTrue); |
| 598 assertSuggestKeywords(STMT_START_IN_LOOP_IN_CLASS, |
| 599 relevance: DART_RELEVANCE_KEYWORD); |
| 600 } |
| 601 |
542 test_empty() { | 602 test_empty() { |
543 addTestSource('^'); | 603 addTestSource('^'); |
544 expect(computeFast(), isTrue); | 604 expect(computeFast(), isTrue); |
545 assertSuggestKeywords(DIRECTIVE_DECLARATION_AND_LIBRARY_KEYWORDS, | 605 assertSuggestKeywords(DIRECTIVE_DECLARATION_AND_LIBRARY_KEYWORDS, |
546 relevance: DART_RELEVANCE_HIGH); | 606 relevance: DART_RELEVANCE_HIGH); |
547 } | 607 } |
548 | 608 |
| 609 test_for_break_continue() { |
| 610 addTestSource('main() {for (int x in myList) {^}}'); |
| 611 expect(computeFast(), isTrue); |
| 612 assertSuggestKeywords(STMT_START_IN_LOOP_OUTSIDE_CLASS, |
| 613 relevance: DART_RELEVANCE_KEYWORD); |
| 614 } |
| 615 |
| 616 test_for_break_continue2() { |
| 617 addTestSource('class A {foo() {for (int x in myList) {^}}}'); |
| 618 expect(computeFast(), isTrue); |
| 619 assertSuggestKeywords(STMT_START_IN_LOOP_IN_CLASS, |
| 620 relevance: DART_RELEVANCE_KEYWORD); |
| 621 } |
| 622 |
549 test_for_expression_in() { | 623 test_for_expression_in() { |
550 addTestSource('main() {for (int x i^)}'); | 624 addTestSource('main() {for (int x i^)}'); |
551 expect(computeFast(), isTrue); | 625 expect(computeFast(), isTrue); |
552 assertSuggestKeywords([Keyword.IN], relevance: DART_RELEVANCE_HIGH); | 626 assertSuggestKeywords([Keyword.IN], relevance: DART_RELEVANCE_HIGH); |
553 } | 627 } |
554 | 628 |
555 test_for_expression_in2() { | 629 test_for_expression_in2() { |
556 addTestSource('main() {for (int x in^)}'); | 630 addTestSource('main() {for (int x in^)}'); |
557 expect(computeFast(), isTrue); | 631 expect(computeFast(), isTrue); |
558 assertSuggestKeywords([Keyword.IN], relevance: DART_RELEVANCE_HIGH); | 632 assertSuggestKeywords([Keyword.IN], relevance: DART_RELEVANCE_HIGH); |
559 } | 633 } |
560 | 634 |
561 test_for_expression_init() { | 635 test_for_expression_init() { |
562 addTestSource('main() {for (int x = i^)}'); | 636 addTestSource('main() {for (int x = i^)}'); |
563 expect(computeFast(), isTrue); | 637 expect(computeFast(), isTrue); |
564 assertSuggestKeywords( | 638 assertSuggestKeywords(EXPRESSION_START_NO_INSTANCE); |
565 [Keyword.FALSE, Keyword.NEW, Keyword.NULL, Keyword.TRUE]); | |
566 } | 639 } |
567 | 640 |
568 test_for_expression_init2() { | 641 test_for_expression_init2() { |
569 addTestSource('main() {for (int x = in^)}'); | 642 addTestSource('main() {for (int x = in^)}'); |
570 expect(computeFast(), isTrue); | 643 expect(computeFast(), isTrue); |
571 assertSuggestKeywords( | 644 assertSuggestKeywords(EXPRESSION_START_NO_INSTANCE); |
572 [Keyword.FALSE, Keyword.NEW, Keyword.NULL, Keyword.TRUE]); | |
573 } | 645 } |
574 | 646 |
575 test_function_async() { | 647 test_function_async() { |
576 addTestSource('main()^'); | 648 addTestSource('main()^'); |
577 expect(computeFast(), isTrue); | 649 expect(computeFast(), isTrue); |
578 assertSuggestKeywords(DECLARATION_KEYWORDS, | 650 assertSuggestKeywords(DECLARATION_KEYWORDS, |
579 pseudoKeywords: ['async'], relevance: DART_RELEVANCE_HIGH); | 651 pseudoKeywords: ['async'], relevance: DART_RELEVANCE_HIGH); |
580 } | 652 } |
581 | 653 |
582 test_function_async2() { | 654 test_function_async2() { |
(...skipping 370 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
953 addTestSource( | 1025 addTestSource( |
954 'library bar; import "zoo.dart"; imp^ import "package:foo/foo.dart";'); | 1026 'library bar; import "zoo.dart"; imp^ import "package:foo/foo.dart";'); |
955 expect(computeFast(), isTrue); | 1027 expect(computeFast(), isTrue); |
956 // TODO(danrubel) should not suggest declaration keywords | 1028 // TODO(danrubel) should not suggest declaration keywords |
957 assertSuggestKeywords(DIRECTIVE_AND_DECLARATION_KEYWORDS, | 1029 assertSuggestKeywords(DIRECTIVE_AND_DECLARATION_KEYWORDS, |
958 relevance: DART_RELEVANCE_HIGH); | 1030 relevance: DART_RELEVANCE_HIGH); |
959 expect(request.replacementOffset, 32); | 1031 expect(request.replacementOffset, 32); |
960 expect(request.replacementLength, 3); | 1032 expect(request.replacementLength, 3); |
961 } | 1033 } |
962 | 1034 |
| 1035 test_is_expression() { |
| 1036 addTestSource('main() {if (x is^)}'); |
| 1037 expect(computeFast(), isTrue); |
| 1038 assertSuggestKeywords([Keyword.IS], relevance: DART_RELEVANCE_HIGH); |
| 1039 } |
| 1040 |
963 test_library() { | 1041 test_library() { |
964 addTestSource('library foo;^'); | 1042 addTestSource('library foo;^'); |
965 expect(computeFast(), isTrue); | 1043 expect(computeFast(), isTrue); |
966 assertSuggestKeywords(DIRECTIVE_AND_DECLARATION_KEYWORDS, | 1044 assertSuggestKeywords(DIRECTIVE_AND_DECLARATION_KEYWORDS, |
967 relevance: DART_RELEVANCE_HIGH); | 1045 relevance: DART_RELEVANCE_HIGH); |
968 } | 1046 } |
969 | 1047 |
970 test_library_declaration() { | 1048 test_library_declaration() { |
971 addTestSource('library ^'); | 1049 addTestSource('library ^'); |
972 expect(computeFast(), isTrue); | 1050 expect(computeFast(), isTrue); |
(...skipping 311 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1284 expect(computeFast(), isTrue); | 1362 expect(computeFast(), isTrue); |
1285 assertSuggestKeywords(STMT_START_IN_SWITCH_OUTSIDE_CLASS); | 1363 assertSuggestKeywords(STMT_START_IN_SWITCH_OUTSIDE_CLASS); |
1286 } | 1364 } |
1287 | 1365 |
1288 test_switch_statement2() { | 1366 test_switch_statement2() { |
1289 addTestSource('class A{foo() {switch(1) {case 1:^}}}'); | 1367 addTestSource('class A{foo() {switch(1) {case 1:^}}}'); |
1290 expect(computeFast(), isTrue); | 1368 expect(computeFast(), isTrue); |
1291 assertSuggestKeywords(STMT_START_IN_SWITCH_IN_CLASS); | 1369 assertSuggestKeywords(STMT_START_IN_SWITCH_IN_CLASS); |
1292 } | 1370 } |
1293 | 1371 |
| 1372 test_while_break_continue() { |
| 1373 addTestSource('main() {while (true) {^}}'); |
| 1374 expect(computeFast(), isTrue); |
| 1375 assertSuggestKeywords(STMT_START_IN_LOOP_OUTSIDE_CLASS, |
| 1376 relevance: DART_RELEVANCE_KEYWORD); |
| 1377 } |
| 1378 |
| 1379 test_while_break_continue2() { |
| 1380 addTestSource('class A {foo() {while (true) {^}}}'); |
| 1381 expect(computeFast(), isTrue); |
| 1382 assertSuggestKeywords(STMT_START_IN_LOOP_IN_CLASS, |
| 1383 relevance: DART_RELEVANCE_KEYWORD); |
| 1384 } |
| 1385 |
1294 void _appendCompletions( | 1386 void _appendCompletions( |
1295 StringBuffer msg, Iterable<String> completions, Iterable<String> other) { | 1387 StringBuffer msg, Iterable<String> completions, Iterable<String> other) { |
1296 List<String> sorted = completions.toList(); | 1388 List<String> sorted = completions.toList(); |
1297 sorted.sort((c1, c2) => c1.compareTo(c2)); | 1389 sorted.sort((c1, c2) => c1.compareTo(c2)); |
1298 sorted.forEach( | 1390 sorted.forEach( |
1299 (c) => msg.writeln(' $c, ${other.contains(c) ? '' : '<<<<<<<<<<<'}')); | 1391 (c) => msg.writeln(' $c, ${other.contains(c) ? '' : '<<<<<<<<<<<'}')); |
1300 } | 1392 } |
1301 | 1393 |
1302 bool _equalSets(Iterable<String> iter1, Iterable<String> iter2) { | 1394 bool _equalSets(Iterable<String> iter1, Iterable<String> iter2) { |
1303 if (iter1.length != iter2.length) return false; | 1395 if (iter1.length != iter2.length) return false; |
1304 if (iter1.any((c) => !iter2.contains(c))) return false; | 1396 if (iter1.any((c) => !iter2.contains(c))) return false; |
1305 if (iter2.any((c) => !iter1.contains(c))) return false; | 1397 if (iter2.any((c) => !iter1.contains(c))) return false; |
1306 return true; | 1398 return true; |
1307 } | 1399 } |
1308 } | 1400 } |
OLD | NEW |