33// BSD-style license that can be found in the LICENSE file.
44
55import 'package:analysis_server/src/cider/completion.dart' ;
6+ import 'package:analyzer/dart/analysis/results.dart' ;
67import 'package:analyzer/source/line_info.dart' ;
8+ import 'package:analyzer/src/test_utilities/function_ast_visitor.dart' ;
79import 'package:analyzer_plugin/protocol/protocol_common.dart'
810 show CompletionSuggestion, CompletionSuggestionKind, ElementKind;
911import 'package:meta/meta.dart' ;
@@ -23,11 +25,11 @@ class CiderCompletionComputerTest extends CiderServiceTest {
2325 final CiderCompletionCache _completionCache = CiderCompletionCache ();
2426
2527 CiderCompletionComputer _computer;
28+ void Function (ResolvedUnitResult ) _testResolvedUnit;
29+
2630 CiderCompletionResult _completionResult;
2731 List <CompletionSuggestion > _suggestions;
2832
29- Future <void > test_limitedResolution_;
30-
3133 @override
3234 void setUp () {
3335 super .setUp ();
@@ -295,10 +297,34 @@ main() {
295297 ]);
296298 }
297299
298- Future <void > test_limitedResolution_class_method () async {
300+ Future <void > test_limitedResolution_class_field_startWithType () async {
301+ _configureToCheckNotResolved (
302+ identifiers: {'print' },
303+ );
304+
305+ await _compute (r'''
306+ class A {
307+ void foo() {
308+ print(0);
309+ }
310+
311+ Str^
312+ }
313+ ''' );
314+
315+ _assertHasClass (text: 'String' );
316+ }
317+
318+ Future <void > test_limitedResolution_class_method_body () async {
319+ _configureToCheckNotResolved (
320+ identifiers: {'print' },
321+ );
322+
299323 await _compute (r'''
300324class A<T> {
301- void foo() {}
325+ void foo() {
326+ print(0);
327+ }
302328
303329 void bar<U>(int a) {
304330 ^
@@ -323,31 +349,44 @@ enum E { e }
323349 _assertHasTypeParameter (text: 'U' );
324350 }
325351
326- Future <void > test_limitedResolution_unit_function () async {
352+ Future <void > test_limitedResolution_class_method_parameterType () async {
353+ _configureToCheckNotResolved (
354+ identifiers: {'print' },
355+ );
356+
327357 await _compute (r'''
328- void foo() {}
358+ class A {
359+ void foo() {
360+ print(0);
361+ }
329362
330- void bar(int a) {
331- ^
363+ void bar(Str^) {}
332364}
333365''' );
334366
335- _assertHasFunction (text: 'foo' );
336- _assertHasParameter (text: 'a' );
367+ _assertHasClass (text: 'String' );
337368 }
338369
339- Future <void > test_localTypeInference () async {
370+ Future <void >
371+ test_limitedResolution_class_method_returnType_hasPartial () async {
372+ _configureToCheckNotResolved (
373+ identifiers: {'print' },
374+ );
375+
340376 await _compute (r'''
341- void foo() {
342- var a = 0;
343- a.^
377+ class A {
378+ void foo() {
379+ print(0);
380+ }
381+
382+ Str^ bar() {}
344383}
345384''' );
346385
347- _assertHasGetter (text: 'isEven ' );
386+ _assertHasClass (text: 'String ' );
348387 }
349388
350- Future <void > test_partialResolution_hasPart () async {
389+ Future <void > test_limitedResolution_hasPart () async {
351390 newFile ('/workspace/dart/test/lib/a.dart' , content: r'''
352391class A {}
353392''' );
@@ -361,6 +400,36 @@ part 'a.dart';
361400 _assertHasClass (text: 'A' );
362401 }
363402
403+ Future <void > test_limitedResolution_unit_function_body () async {
404+ _configureToCheckNotResolved (
405+ identifiers: {'print' },
406+ );
407+
408+ await _compute (r'''
409+ void foo() {
410+ print(0);
411+ }
412+
413+ void bar(int a) {
414+ ^
415+ }
416+ ''' );
417+
418+ _assertHasFunction (text: 'foo' );
419+ _assertHasParameter (text: 'a' );
420+ }
421+
422+ Future <void > test_localTypeInference () async {
423+ await _compute (r'''
424+ void foo() {
425+ var a = 0;
426+ a.^
427+ }
428+ ''' );
429+
430+ _assertHasGetter (text: 'isEven' );
431+ }
432+
364433 Future <void > test_warmUp_cachesImportedLibraries () async {
365434 var aPath = convertPath ('/workspace/dart/test/lib/a.dart' );
366435 newFile (aPath, content: r'''
@@ -550,10 +619,28 @@ import 'a.dart';
550619 path: convertPath (testPath),
551620 line: context.line,
552621 column: context.character,
622+ testResolvedUnit: _testResolvedUnit,
553623 );
554624 _suggestions = _completionResult.suggestions;
555625 }
556626
627+ /// Configure the [CiderCompletionComputer] to check that when resolving
628+ /// for completion we don't resolve unnecessary node.
629+ void _configureToCheckNotResolved ({Set <String > identifiers}) {
630+ _testResolvedUnit = (resolvedUnitResult) {
631+ var unit = resolvedUnitResult.unit;
632+ unit.accept (
633+ FunctionAstVisitor (
634+ simpleIdentifier: (node) {
635+ if (identifiers.contains (node.name) && node.staticElement != null ) {
636+ fail ('Unexpectedly resolved node: $node ' );
637+ }
638+ },
639+ ),
640+ );
641+ };
642+ }
643+
557644 /// TODO(scheglov) Implement incremental updating
558645 void _createFileResolver () {
559646 createFileResolver ();
0 commit comments