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

Side by Side Diff: pkg/analyzer/test/generated/simple_resolver_test.dart

Issue 1782463002: Split resolver_test.dart into smaller files. (Closed) Base URL: https://github.com/dart-lang/sdk.git@master
Patch Set: Created 4 years, 9 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
OLDNEW
(Empty)
1 // Copyright (c) 2016, the Dart project authors. Please see the AUTHORS file
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.
4
5 library analyzer.test.generated.simple_resolver_test;
6
7 import 'package:analyzer/dart/ast/ast.dart';
8 import 'package:analyzer/dart/ast/visitor.dart';
9 import 'package:analyzer/dart/element/element.dart';
10 import 'package:analyzer/dart/element/type.dart';
11 import 'package:analyzer/src/generated/engine.dart';
12 import 'package:analyzer/src/generated/error.dart';
13 import 'package:analyzer/src/generated/java_engine.dart';
14 import 'package:analyzer/src/generated/source_io.dart';
15 import 'package:unittest/unittest.dart';
16
17 import '../reflective_tests.dart';
18 import '../utils.dart';
19 import 'resolver_test_case.dart';
20 import 'test_support.dart';
21
22 main() {
23 initializeTestEnvironment();
24 runReflectiveTests(SimpleResolverTest);
25 }
26
27 @reflectiveTest
28 class SimpleResolverTest extends ResolverTestCase {
29 void fail_getter_and_setter_fromMixins_property_access() {
30 // TODO(paulberry): it appears that auxiliaryElements isn't properly set on
31 // a SimpleIdentifier that's inside a property access. This bug should be
32 // fixed.
33 Source source = addSource('''
34 class B {}
35 class M1 {
36 get x => null;
37 set x(value) {}
38 }
39 class M2 {
40 get x => null;
41 set x(value) {}
42 }
43 class C extends B with M1, M2 {}
44 void main() {
45 new C().x += 1;
46 }
47 ''');
48 LibraryElement library = resolve2(source);
49 assertNoErrors(source);
50 verify([source]);
51 // Verify that both the getter and setter for "x" in "new C().x" refer to
52 // the accessors defined in M2.
53 FunctionDeclaration main =
54 library.definingCompilationUnit.functions[0].computeNode();
55 BlockFunctionBody body = main.functionExpression.body;
56 ExpressionStatement stmt = body.block.statements[0];
57 AssignmentExpression assignment = stmt.expression;
58 PropertyAccess propertyAccess = assignment.leftHandSide;
59 expect(
60 propertyAccess.propertyName.staticElement.enclosingElement.name, 'M2');
61 expect(
62 propertyAccess
63 .propertyName.auxiliaryElements.staticElement.enclosingElement.name,
64 'M2');
65 }
66
67 void fail_staticInvocation() {
68 Source source = addSource(r'''
69 class A {
70 static int get g => (a,b) => 0;
71 }
72 class B {
73 f() {
74 A.g(1,0);
75 }
76 }''');
77 computeLibrarySourceErrors(source);
78 assertNoErrors(source);
79 verify([source]);
80 }
81
82 void test_argumentResolution_required_matching() {
83 Source source = addSource(r'''
84 class A {
85 void f() {
86 g(1, 2, 3);
87 }
88 void g(a, b, c) {}
89 }''');
90 _validateArgumentResolution(source, [0, 1, 2]);
91 }
92
93 void test_argumentResolution_required_tooFew() {
94 Source source = addSource(r'''
95 class A {
96 void f() {
97 g(1, 2);
98 }
99 void g(a, b, c) {}
100 }''');
101 _validateArgumentResolution(source, [0, 1]);
102 }
103
104 void test_argumentResolution_required_tooMany() {
105 Source source = addSource(r'''
106 class A {
107 void f() {
108 g(1, 2, 3);
109 }
110 void g(a, b) {}
111 }''');
112 _validateArgumentResolution(source, [0, 1, -1]);
113 }
114
115 void test_argumentResolution_requiredAndNamed_extra() {
116 Source source = addSource(r'''
117 class A {
118 void f() {
119 g(1, 2, c: 3, d: 4);
120 }
121 void g(a, b, {c}) {}
122 }''');
123 _validateArgumentResolution(source, [0, 1, 2, -1]);
124 }
125
126 void test_argumentResolution_requiredAndNamed_matching() {
127 Source source = addSource(r'''
128 class A {
129 void f() {
130 g(1, 2, c: 3);
131 }
132 void g(a, b, {c}) {}
133 }''');
134 _validateArgumentResolution(source, [0, 1, 2]);
135 }
136
137 void test_argumentResolution_requiredAndNamed_missing() {
138 Source source = addSource(r'''
139 class A {
140 void f() {
141 g(1, 2, d: 3);
142 }
143 void g(a, b, {c, d}) {}
144 }''');
145 _validateArgumentResolution(source, [0, 1, 3]);
146 }
147
148 void test_argumentResolution_requiredAndPositional_fewer() {
149 Source source = addSource(r'''
150 class A {
151 void f() {
152 g(1, 2, 3);
153 }
154 void g(a, b, [c, d]) {}
155 }''');
156 _validateArgumentResolution(source, [0, 1, 2]);
157 }
158
159 void test_argumentResolution_requiredAndPositional_matching() {
160 Source source = addSource(r'''
161 class A {
162 void f() {
163 g(1, 2, 3, 4);
164 }
165 void g(a, b, [c, d]) {}
166 }''');
167 _validateArgumentResolution(source, [0, 1, 2, 3]);
168 }
169
170 void test_argumentResolution_requiredAndPositional_more() {
171 Source source = addSource(r'''
172 class A {
173 void f() {
174 g(1, 2, 3, 4);
175 }
176 void g(a, b, [c]) {}
177 }''');
178 _validateArgumentResolution(source, [0, 1, 2, -1]);
179 }
180
181 void test_argumentResolution_setter_propagated() {
182 Source source = addSource(r'''
183 main() {
184 var a = new A();
185 a.sss = 0;
186 }
187 class A {
188 set sss(x) {}
189 }''');
190 LibraryElement library = resolve2(source);
191 CompilationUnitElement unit = library.definingCompilationUnit;
192 // find "a.sss = 0"
193 AssignmentExpression assignment;
194 {
195 FunctionElement mainElement = unit.functions[0];
196 FunctionBody mainBody = mainElement.computeNode().functionExpression.body;
197 Statement statement = (mainBody as BlockFunctionBody).block.statements[1];
198 ExpressionStatement expressionStatement =
199 statement as ExpressionStatement;
200 assignment = expressionStatement.expression as AssignmentExpression;
201 }
202 // get parameter
203 Expression rhs = assignment.rightHandSide;
204 expect(rhs.staticParameterElement, isNull);
205 ParameterElement parameter = rhs.propagatedParameterElement;
206 expect(parameter, isNotNull);
207 expect(parameter.displayName, "x");
208 // validate
209 ClassElement classA = unit.types[0];
210 PropertyAccessorElement setter = classA.accessors[0];
211 expect(setter.parameters[0], same(parameter));
212 }
213
214 void test_argumentResolution_setter_propagated_propertyAccess() {
215 Source source = addSource(r'''
216 main() {
217 var a = new A();
218 a.b.sss = 0;
219 }
220 class A {
221 B b = new B();
222 }
223 class B {
224 set sss(x) {}
225 }''');
226 LibraryElement library = resolve2(source);
227 CompilationUnitElement unit = library.definingCompilationUnit;
228 // find "a.b.sss = 0"
229 AssignmentExpression assignment;
230 {
231 FunctionElement mainElement = unit.functions[0];
232 FunctionBody mainBody = mainElement.computeNode().functionExpression.body;
233 Statement statement = (mainBody as BlockFunctionBody).block.statements[1];
234 ExpressionStatement expressionStatement =
235 statement as ExpressionStatement;
236 assignment = expressionStatement.expression as AssignmentExpression;
237 }
238 // get parameter
239 Expression rhs = assignment.rightHandSide;
240 expect(rhs.staticParameterElement, isNull);
241 ParameterElement parameter = rhs.propagatedParameterElement;
242 expect(parameter, isNotNull);
243 expect(parameter.displayName, "x");
244 // validate
245 ClassElement classB = unit.types[1];
246 PropertyAccessorElement setter = classB.accessors[0];
247 expect(setter.parameters[0], same(parameter));
248 }
249
250 void test_argumentResolution_setter_static() {
251 Source source = addSource(r'''
252 main() {
253 A a = new A();
254 a.sss = 0;
255 }
256 class A {
257 set sss(x) {}
258 }''');
259 LibraryElement library = resolve2(source);
260 CompilationUnitElement unit = library.definingCompilationUnit;
261 // find "a.sss = 0"
262 AssignmentExpression assignment;
263 {
264 FunctionElement mainElement = unit.functions[0];
265 FunctionBody mainBody = mainElement.computeNode().functionExpression.body;
266 Statement statement = (mainBody as BlockFunctionBody).block.statements[1];
267 ExpressionStatement expressionStatement =
268 statement as ExpressionStatement;
269 assignment = expressionStatement.expression as AssignmentExpression;
270 }
271 // get parameter
272 Expression rhs = assignment.rightHandSide;
273 ParameterElement parameter = rhs.staticParameterElement;
274 expect(parameter, isNotNull);
275 expect(parameter.displayName, "x");
276 // validate
277 ClassElement classA = unit.types[0];
278 PropertyAccessorElement setter = classA.accessors[0];
279 expect(setter.parameters[0], same(parameter));
280 }
281
282 void test_argumentResolution_setter_static_propertyAccess() {
283 Source source = addSource(r'''
284 main() {
285 A a = new A();
286 a.b.sss = 0;
287 }
288 class A {
289 B b = new B();
290 }
291 class B {
292 set sss(x) {}
293 }''');
294 LibraryElement library = resolve2(source);
295 CompilationUnitElement unit = library.definingCompilationUnit;
296 // find "a.b.sss = 0"
297 AssignmentExpression assignment;
298 {
299 FunctionElement mainElement = unit.functions[0];
300 FunctionBody mainBody = mainElement.computeNode().functionExpression.body;
301 Statement statement = (mainBody as BlockFunctionBody).block.statements[1];
302 ExpressionStatement expressionStatement =
303 statement as ExpressionStatement;
304 assignment = expressionStatement.expression as AssignmentExpression;
305 }
306 // get parameter
307 Expression rhs = assignment.rightHandSide;
308 ParameterElement parameter = rhs.staticParameterElement;
309 expect(parameter, isNotNull);
310 expect(parameter.displayName, "x");
311 // validate
312 ClassElement classB = unit.types[1];
313 PropertyAccessorElement setter = classB.accessors[0];
314 expect(setter.parameters[0], same(parameter));
315 }
316
317 void test_breakTarget_labeled() {
318 // Verify that the target of the label is correctly found and is recorded
319 // as the unlabeled portion of the statement.
320 String text = r'''
321 void f() {
322 loop1: while (true) {
323 loop2: for (int i = 0; i < 10; i++) {
324 break loop1;
325 break loop2;
326 }
327 }
328 }
329 ''';
330 CompilationUnit unit = resolveSource(text);
331 WhileStatement whileStatement = EngineTestCase.findNode(
332 unit, text, 'while (true)', (n) => n is WhileStatement);
333 ForStatement forStatement =
334 EngineTestCase.findNode(unit, text, 'for', (n) => n is ForStatement);
335 BreakStatement break1 = EngineTestCase.findNode(
336 unit, text, 'break loop1', (n) => n is BreakStatement);
337 BreakStatement break2 = EngineTestCase.findNode(
338 unit, text, 'break loop2', (n) => n is BreakStatement);
339 expect(break1.target, same(whileStatement));
340 expect(break2.target, same(forStatement));
341 }
342
343 void test_breakTarget_unlabeledBreakFromDo() {
344 String text = r'''
345 void f() {
346 do {
347 break;
348 } while (true);
349 }
350 ''';
351 CompilationUnit unit = resolveSource(text);
352 DoStatement doStatement =
353 EngineTestCase.findNode(unit, text, 'do', (n) => n is DoStatement);
354 BreakStatement breakStatement = EngineTestCase.findNode(
355 unit, text, 'break', (n) => n is BreakStatement);
356 expect(breakStatement.target, same(doStatement));
357 }
358
359 void test_breakTarget_unlabeledBreakFromFor() {
360 String text = r'''
361 void f() {
362 for (int i = 0; i < 10; i++) {
363 break;
364 }
365 }
366 ''';
367 CompilationUnit unit = resolveSource(text);
368 ForStatement forStatement =
369 EngineTestCase.findNode(unit, text, 'for', (n) => n is ForStatement);
370 BreakStatement breakStatement = EngineTestCase.findNode(
371 unit, text, 'break', (n) => n is BreakStatement);
372 expect(breakStatement.target, same(forStatement));
373 }
374
375 void test_breakTarget_unlabeledBreakFromForEach() {
376 String text = r'''
377 void f() {
378 for (x in []) {
379 break;
380 }
381 }
382 ''';
383 CompilationUnit unit = resolveSource(text);
384 ForEachStatement forStatement = EngineTestCase.findNode(
385 unit, text, 'for', (n) => n is ForEachStatement);
386 BreakStatement breakStatement = EngineTestCase.findNode(
387 unit, text, 'break', (n) => n is BreakStatement);
388 expect(breakStatement.target, same(forStatement));
389 }
390
391 void test_breakTarget_unlabeledBreakFromSwitch() {
392 String text = r'''
393 void f() {
394 while (true) {
395 switch (0) {
396 case 0:
397 break;
398 }
399 }
400 }
401 ''';
402 CompilationUnit unit = resolveSource(text);
403 SwitchStatement switchStatement = EngineTestCase.findNode(
404 unit, text, 'switch', (n) => n is SwitchStatement);
405 BreakStatement breakStatement = EngineTestCase.findNode(
406 unit, text, 'break', (n) => n is BreakStatement);
407 expect(breakStatement.target, same(switchStatement));
408 }
409
410 void test_breakTarget_unlabeledBreakFromWhile() {
411 String text = r'''
412 void f() {
413 while (true) {
414 break;
415 }
416 }
417 ''';
418 CompilationUnit unit = resolveSource(text);
419 WhileStatement whileStatement = EngineTestCase.findNode(
420 unit, text, 'while', (n) => n is WhileStatement);
421 BreakStatement breakStatement = EngineTestCase.findNode(
422 unit, text, 'break', (n) => n is BreakStatement);
423 expect(breakStatement.target, same(whileStatement));
424 }
425
426 void test_breakTarget_unlabeledBreakToOuterFunction() {
427 // Verify that unlabeled break statements can't resolve to loops in an
428 // outer function.
429 String text = r'''
430 void f() {
431 while (true) {
432 void g() {
433 break;
434 }
435 }
436 }
437 ''';
438 CompilationUnit unit = resolveSource(text);
439 BreakStatement breakStatement = EngineTestCase.findNode(
440 unit, text, 'break', (n) => n is BreakStatement);
441 expect(breakStatement.target, isNull);
442 }
443
444 void test_class_definesCall() {
445 Source source = addSource(r'''
446 class A {
447 int call(int x) { return x; }
448 }
449 int f(A a) {
450 return a(0);
451 }''');
452 computeLibrarySourceErrors(source);
453 assertNoErrors(source);
454 verify([source]);
455 }
456
457 void test_class_extends_implements() {
458 Source source = addSource(r'''
459 class A extends B implements C {}
460 class B {}
461 class C {}''');
462 computeLibrarySourceErrors(source);
463 assertNoErrors(source);
464 verify([source]);
465 }
466
467 void test_commentReference_class() {
468 Source source = addSource(r'''
469 f() {}
470 /** [A] [new A] [A.n] [new A.n] [m] [f] */
471 class A {
472 A() {}
473 A.n() {}
474 m() {}
475 }''');
476 computeLibrarySourceErrors(source);
477 assertNoErrors(source);
478 verify([source]);
479 }
480
481 void test_commentReference_parameter() {
482 Source source = addSource(r'''
483 class A {
484 A() {}
485 A.n() {}
486 /** [e] [f] */
487 m(e, f()) {}
488 }''');
489 computeLibrarySourceErrors(source);
490 assertNoErrors(source);
491 verify([source]);
492 }
493
494 void test_commentReference_singleLine() {
495 Source source = addSource(r'''
496 /// [A]
497 class A {}''');
498 computeLibrarySourceErrors(source);
499 assertNoErrors(source);
500 verify([source]);
501 }
502
503 void test_continueTarget_labeled() {
504 // Verify that the target of the label is correctly found and is recorded
505 // as the unlabeled portion of the statement.
506 String text = r'''
507 void f() {
508 loop1: while (true) {
509 loop2: for (int i = 0; i < 10; i++) {
510 continue loop1;
511 continue loop2;
512 }
513 }
514 }
515 ''';
516 CompilationUnit unit = resolveSource(text);
517 WhileStatement whileStatement = EngineTestCase.findNode(
518 unit, text, 'while (true)', (n) => n is WhileStatement);
519 ForStatement forStatement =
520 EngineTestCase.findNode(unit, text, 'for', (n) => n is ForStatement);
521 ContinueStatement continue1 = EngineTestCase.findNode(
522 unit, text, 'continue loop1', (n) => n is ContinueStatement);
523 ContinueStatement continue2 = EngineTestCase.findNode(
524 unit, text, 'continue loop2', (n) => n is ContinueStatement);
525 expect(continue1.target, same(whileStatement));
526 expect(continue2.target, same(forStatement));
527 }
528
529 void test_continueTarget_unlabeledContinueFromDo() {
530 String text = r'''
531 void f() {
532 do {
533 continue;
534 } while (true);
535 }
536 ''';
537 CompilationUnit unit = resolveSource(text);
538 DoStatement doStatement =
539 EngineTestCase.findNode(unit, text, 'do', (n) => n is DoStatement);
540 ContinueStatement continueStatement = EngineTestCase.findNode(
541 unit, text, 'continue', (n) => n is ContinueStatement);
542 expect(continueStatement.target, same(doStatement));
543 }
544
545 void test_continueTarget_unlabeledContinueFromFor() {
546 String text = r'''
547 void f() {
548 for (int i = 0; i < 10; i++) {
549 continue;
550 }
551 }
552 ''';
553 CompilationUnit unit = resolveSource(text);
554 ForStatement forStatement =
555 EngineTestCase.findNode(unit, text, 'for', (n) => n is ForStatement);
556 ContinueStatement continueStatement = EngineTestCase.findNode(
557 unit, text, 'continue', (n) => n is ContinueStatement);
558 expect(continueStatement.target, same(forStatement));
559 }
560
561 void test_continueTarget_unlabeledContinueFromForEach() {
562 String text = r'''
563 void f() {
564 for (x in []) {
565 continue;
566 }
567 }
568 ''';
569 CompilationUnit unit = resolveSource(text);
570 ForEachStatement forStatement = EngineTestCase.findNode(
571 unit, text, 'for', (n) => n is ForEachStatement);
572 ContinueStatement continueStatement = EngineTestCase.findNode(
573 unit, text, 'continue', (n) => n is ContinueStatement);
574 expect(continueStatement.target, same(forStatement));
575 }
576
577 void test_continueTarget_unlabeledContinueFromWhile() {
578 String text = r'''
579 void f() {
580 while (true) {
581 continue;
582 }
583 }
584 ''';
585 CompilationUnit unit = resolveSource(text);
586 WhileStatement whileStatement = EngineTestCase.findNode(
587 unit, text, 'while', (n) => n is WhileStatement);
588 ContinueStatement continueStatement = EngineTestCase.findNode(
589 unit, text, 'continue', (n) => n is ContinueStatement);
590 expect(continueStatement.target, same(whileStatement));
591 }
592
593 void test_continueTarget_unlabeledContinueSkipsSwitch() {
594 String text = r'''
595 void f() {
596 while (true) {
597 switch (0) {
598 case 0:
599 continue;
600 }
601 }
602 }
603 ''';
604 CompilationUnit unit = resolveSource(text);
605 WhileStatement whileStatement = EngineTestCase.findNode(
606 unit, text, 'while', (n) => n is WhileStatement);
607 ContinueStatement continueStatement = EngineTestCase.findNode(
608 unit, text, 'continue', (n) => n is ContinueStatement);
609 expect(continueStatement.target, same(whileStatement));
610 }
611
612 void test_continueTarget_unlabeledContinueToOuterFunction() {
613 // Verify that unlabeled continue statements can't resolve to loops in an
614 // outer function.
615 String text = r'''
616 void f() {
617 while (true) {
618 void g() {
619 continue;
620 }
621 }
622 }
623 ''';
624 CompilationUnit unit = resolveSource(text);
625 ContinueStatement continueStatement = EngineTestCase.findNode(
626 unit, text, 'continue', (n) => n is ContinueStatement);
627 expect(continueStatement.target, isNull);
628 }
629
630 void test_empty() {
631 Source source = addSource("");
632 computeLibrarySourceErrors(source);
633 assertNoErrors(source);
634 verify([source]);
635 }
636
637 void test_entryPoint_exported() {
638 addNamedSource(
639 "/two.dart",
640 r'''
641 library two;
642 main() {}''');
643 Source source = addNamedSource(
644 "/one.dart",
645 r'''
646 library one;
647 export 'two.dart';''');
648 LibraryElement library = resolve2(source);
649 expect(library, isNotNull);
650 FunctionElement main = library.entryPoint;
651 expect(main, isNotNull);
652 expect(main.library, isNot(same(library)));
653 assertNoErrors(source);
654 verify([source]);
655 }
656
657 void test_entryPoint_local() {
658 Source source = addNamedSource(
659 "/one.dart",
660 r'''
661 library one;
662 main() {}''');
663 LibraryElement library = resolve2(source);
664 expect(library, isNotNull);
665 FunctionElement main = library.entryPoint;
666 expect(main, isNotNull);
667 expect(main.library, same(library));
668 assertNoErrors(source);
669 verify([source]);
670 }
671
672 void test_entryPoint_none() {
673 Source source = addNamedSource("/one.dart", "library one;");
674 LibraryElement library = resolve2(source);
675 expect(library, isNotNull);
676 expect(library.entryPoint, isNull);
677 assertNoErrors(source);
678 verify([source]);
679 }
680
681 void test_enum_externalLibrary() {
682 addNamedSource(
683 "/my_lib.dart",
684 r'''
685 library my_lib;
686 enum EEE {A, B, C}''');
687 Source source = addSource(r'''
688 import 'my_lib.dart';
689 main() {
690 EEE e = null;
691 }''');
692 computeLibrarySourceErrors(source);
693 assertNoErrors(source);
694 verify([source]);
695 }
696
697 void test_extractedMethodAsConstant() {
698 Source source = addSource(r'''
699 abstract class Comparable<T> {
700 int compareTo(T other);
701 static int compare(Comparable a, Comparable b) => a.compareTo(b);
702 }
703 class A {
704 void sort([compare = Comparable.compare]) {}
705 }''');
706 computeLibrarySourceErrors(source);
707 assertNoErrors(source);
708 verify([source]);
709 }
710
711 void test_fieldFormalParameter() {
712 Source source = addSource(r'''
713 class A {
714 int x;
715 A(this.x) {}
716 }''');
717 computeLibrarySourceErrors(source);
718 assertNoErrors(source);
719 verify([source]);
720 }
721
722 void test_forEachLoops_nonConflicting() {
723 Source source = addSource(r'''
724 f() {
725 List list = [1,2,3];
726 for (int x in list) {}
727 for (int x in list) {}
728 }''');
729 computeLibrarySourceErrors(source);
730 assertNoErrors(source);
731 verify([source]);
732 }
733
734 void test_forLoops_nonConflicting() {
735 Source source = addSource(r'''
736 f() {
737 for (int i = 0; i < 3; i++) {
738 }
739 for (int i = 0; i < 3; i++) {
740 }
741 }''');
742 computeLibrarySourceErrors(source);
743 assertNoErrors(source);
744 verify([source]);
745 }
746
747 void test_functionTypeAlias() {
748 Source source = addSource(r'''
749 typedef bool P(e);
750 class A {
751 P p;
752 m(e) {
753 if (p(e)) {}
754 }
755 }''');
756 computeLibrarySourceErrors(source);
757 assertNoErrors(source);
758 verify([source]);
759 }
760
761 void test_getter_and_setter_fromMixins_bare_identifier() {
762 Source source = addSource('''
763 class B {}
764 class M1 {
765 get x => null;
766 set x(value) {}
767 }
768 class M2 {
769 get x => null;
770 set x(value) {}
771 }
772 class C extends B with M1, M2 {
773 void f() {
774 x += 1;
775 }
776 }
777 ''');
778 LibraryElement library = resolve2(source);
779 assertNoErrors(source);
780 verify([source]);
781 // Verify that both the getter and setter for "x" in C.f() refer to the
782 // accessors defined in M2.
783 ClassElement classC = library.definingCompilationUnit.types[3];
784 MethodDeclaration f = classC.getMethod('f').computeNode();
785 BlockFunctionBody body = f.body;
786 ExpressionStatement stmt = body.block.statements[0];
787 AssignmentExpression assignment = stmt.expression;
788 SimpleIdentifier leftHandSide = assignment.leftHandSide;
789 expect(leftHandSide.staticElement.enclosingElement.name, 'M2');
790 expect(leftHandSide.auxiliaryElements.staticElement.enclosingElement.name,
791 'M2');
792 }
793
794 void test_getter_fromMixins_bare_identifier() {
795 Source source = addSource('''
796 class B {}
797 class M1 {
798 get x => null;
799 }
800 class M2 {
801 get x => null;
802 }
803 class C extends B with M1, M2 {
804 f() {
805 return x;
806 }
807 }
808 ''');
809 LibraryElement library = resolve2(source);
810 assertNoErrors(source);
811 verify([source]);
812 // Verify that the getter for "x" in C.f() refers to the getter defined in
813 // M2.
814 ClassElement classC = library.definingCompilationUnit.types[3];
815 MethodDeclaration f = classC.getMethod('f').computeNode();
816 BlockFunctionBody body = f.body;
817 ReturnStatement stmt = body.block.statements[0];
818 SimpleIdentifier x = stmt.expression;
819 expect(x.staticElement.enclosingElement.name, 'M2');
820 }
821
822 void test_getter_fromMixins_property_access() {
823 Source source = addSource('''
824 class B {}
825 class M1 {
826 get x => null;
827 }
828 class M2 {
829 get x => null;
830 }
831 class C extends B with M1, M2 {}
832 void main() {
833 var y = new C().x;
834 }
835 ''');
836 LibraryElement library = resolve2(source);
837 assertNoErrors(source);
838 verify([source]);
839 // Verify that the getter for "x" in "new C().x" refers to the getter
840 // defined in M2.
841 FunctionDeclaration main =
842 library.definingCompilationUnit.functions[0].computeNode();
843 BlockFunctionBody body = main.functionExpression.body;
844 VariableDeclarationStatement stmt = body.block.statements[0];
845 PropertyAccess propertyAccess = stmt.variables.variables[0].initializer;
846 expect(
847 propertyAccess.propertyName.staticElement.enclosingElement.name, 'M2');
848 }
849
850 void test_getterAndSetterWithDifferentTypes() {
851 Source source = addSource(r'''
852 class A {
853 int get f => 0;
854 void set f(String s) {}
855 }
856 g (A a) {
857 a.f = a.f.toString();
858 }''');
859 computeLibrarySourceErrors(source);
860 assertErrors(
861 source, [StaticWarningCode.MISMATCHED_GETTER_AND_SETTER_TYPES]);
862 verify([source]);
863 }
864
865 void test_hasReferenceToSuper() {
866 Source source = addSource(r'''
867 class A {}
868 class B {toString() => super.toString();}''');
869 LibraryElement library = resolve2(source);
870 expect(library, isNotNull);
871 CompilationUnitElement unit = library.definingCompilationUnit;
872 expect(unit, isNotNull);
873 List<ClassElement> classes = unit.types;
874 expect(classes, hasLength(2));
875 expect(classes[0].hasReferenceToSuper, isFalse);
876 expect(classes[1].hasReferenceToSuper, isTrue);
877 assertNoErrors(source);
878 verify([source]);
879 }
880
881 void test_import_hide() {
882 addNamedSource(
883 "/lib1.dart",
884 r'''
885 library lib1;
886 set foo(value) {}
887 class A {}''');
888 addNamedSource(
889 "/lib2.dart",
890 r'''
891 library lib2;
892 set foo(value) {}''');
893 Source source = addNamedSource(
894 "/lib3.dart",
895 r'''
896 import 'lib1.dart' hide foo;
897 import 'lib2.dart';
898
899 main() {
900 foo = 0;
901 }
902 A a;''');
903 computeLibrarySourceErrors(source);
904 assertNoErrors(source);
905 verify([source]);
906 }
907
908 void test_import_prefix() {
909 addNamedSource(
910 "/two.dart",
911 r'''
912 library two;
913 f(int x) {
914 return x * x;
915 }''');
916 Source source = addNamedSource(
917 "/one.dart",
918 r'''
919 library one;
920 import 'two.dart' as _two;
921 main() {
922 _two.f(0);
923 }''');
924 computeLibrarySourceErrors(source);
925 assertNoErrors(source);
926 verify([source]);
927 }
928
929 void test_import_spaceInUri() {
930 addNamedSource(
931 "/sub folder/lib.dart",
932 r'''
933 library lib;
934 foo() {}''');
935 Source source = addNamedSource(
936 "/app.dart",
937 r'''
938 import 'sub folder/lib.dart';
939
940 main() {
941 foo();
942 }''');
943 computeLibrarySourceErrors(source);
944 assertNoErrors(source);
945 verify([source]);
946 }
947
948 void test_indexExpression_typeParameters() {
949 Source source = addSource(r'''
950 f() {
951 List<int> a;
952 a[0];
953 List<List<int>> b;
954 b[0][0];
955 List<List<List<int>>> c;
956 c[0][0][0];
957 }''');
958 computeLibrarySourceErrors(source);
959 assertNoErrors(source);
960 verify([source]);
961 }
962
963 void test_indexExpression_typeParameters_invalidAssignmentWarning() {
964 Source source = addSource(r'''
965 f() {
966 List<List<int>> b;
967 b[0][0] = 'hi';
968 }''');
969 computeLibrarySourceErrors(source);
970 assertErrors(source, [StaticTypeWarningCode.INVALID_ASSIGNMENT]);
971 verify([source]);
972 }
973
974 void test_indirectOperatorThroughCall() {
975 Source source = addSource(r'''
976 class A {
977 B call() { return new B(); }
978 }
979
980 class B {
981 int operator [](int i) { return i; }
982 }
983
984 A f = new A();
985
986 g(int x) {}
987
988 main() {
989 g(f()[0]);
990 }''');
991 computeLibrarySourceErrors(source);
992 assertNoErrors(source);
993 verify([source]);
994 }
995
996 void test_invoke_dynamicThroughGetter() {
997 Source source = addSource(r'''
998 class A {
999 List get X => [() => 0];
1000 m(A a) {
1001 X.last;
1002 }
1003 }''');
1004 computeLibrarySourceErrors(source);
1005 assertNoErrors(source);
1006 verify([source]);
1007 }
1008
1009 void test_isValidMixin_badSuperclass() {
1010 Source source = addSource(r'''
1011 class A extends B {}
1012 class B {}
1013 class C = Object with A;''');
1014 LibraryElement library = resolve2(source);
1015 expect(library, isNotNull);
1016 CompilationUnitElement unit = library.definingCompilationUnit;
1017 expect(unit, isNotNull);
1018 ClassElement a = unit.getType('A');
1019 expect(a.isValidMixin, isFalse);
1020 assertErrors(source, [CompileTimeErrorCode.MIXIN_INHERITS_FROM_NOT_OBJECT]);
1021 verify([source]);
1022 }
1023
1024 void test_isValidMixin_badSuperclass_withSuperMixins() {
1025 resetWithOptions(new AnalysisOptionsImpl()..enableSuperMixins = true);
1026 Source source = addSource(r'''
1027 class A extends B {}
1028 class B {}
1029 class C = Object with A;''');
1030 LibraryElement library = resolve2(source);
1031 expect(library, isNotNull);
1032 CompilationUnitElement unit = library.definingCompilationUnit;
1033 expect(unit, isNotNull);
1034 ClassElement a = unit.getType('A');
1035 expect(a.isValidMixin, isTrue);
1036 assertNoErrors(source);
1037 verify([source]);
1038 }
1039
1040 void test_isValidMixin_constructor() {
1041 Source source = addSource(r'''
1042 class A {
1043 A() {}
1044 }
1045 class C = Object with A;''');
1046 LibraryElement library = resolve2(source);
1047 expect(library, isNotNull);
1048 CompilationUnitElement unit = library.definingCompilationUnit;
1049 expect(unit, isNotNull);
1050 ClassElement a = unit.getType('A');
1051 expect(a.isValidMixin, isFalse);
1052 assertErrors(source, [CompileTimeErrorCode.MIXIN_DECLARES_CONSTRUCTOR]);
1053 verify([source]);
1054 }
1055
1056 void test_isValidMixin_constructor_withSuperMixins() {
1057 resetWithOptions(new AnalysisOptionsImpl()..enableSuperMixins = true);
1058 Source source = addSource(r'''
1059 class A {
1060 A() {}
1061 }
1062 class C = Object with A;''');
1063 LibraryElement library = resolve2(source);
1064 expect(library, isNotNull);
1065 CompilationUnitElement unit = library.definingCompilationUnit;
1066 expect(unit, isNotNull);
1067 ClassElement a = unit.getType('A');
1068 expect(a.isValidMixin, isFalse);
1069 assertErrors(source, [CompileTimeErrorCode.MIXIN_DECLARES_CONSTRUCTOR]);
1070 verify([source]);
1071 }
1072
1073 void test_isValidMixin_factoryConstructor() {
1074 Source source = addSource(r'''
1075 class A {
1076 factory A() => null;
1077 }
1078 class C = Object with A;''');
1079 LibraryElement library = resolve2(source);
1080 expect(library, isNotNull);
1081 CompilationUnitElement unit = library.definingCompilationUnit;
1082 expect(unit, isNotNull);
1083 ClassElement a = unit.getType('A');
1084 expect(a.isValidMixin, isTrue);
1085 assertNoErrors(source);
1086 verify([source]);
1087 }
1088
1089 void test_isValidMixin_factoryConstructor_withSuperMixins() {
1090 resetWithOptions(new AnalysisOptionsImpl()..enableSuperMixins = true);
1091 Source source = addSource(r'''
1092 class A {
1093 factory A() => null;
1094 }
1095 class C = Object with A;''');
1096 LibraryElement library = resolve2(source);
1097 expect(library, isNotNull);
1098 CompilationUnitElement unit = library.definingCompilationUnit;
1099 expect(unit, isNotNull);
1100 ClassElement a = unit.getType('A');
1101 expect(a.isValidMixin, isTrue);
1102 assertNoErrors(source);
1103 verify([source]);
1104 }
1105
1106 void test_isValidMixin_super() {
1107 Source source = addSource(r'''
1108 class A {
1109 toString() {
1110 return super.toString();
1111 }
1112 }
1113 class C = Object with A;''');
1114 LibraryElement library = resolve2(source);
1115 expect(library, isNotNull);
1116 CompilationUnitElement unit = library.definingCompilationUnit;
1117 expect(unit, isNotNull);
1118 ClassElement a = unit.getType('A');
1119 expect(a.isValidMixin, isFalse);
1120 assertErrors(source, [CompileTimeErrorCode.MIXIN_REFERENCES_SUPER]);
1121 verify([source]);
1122 }
1123
1124 void test_isValidMixin_super_withSuperMixins() {
1125 resetWithOptions(new AnalysisOptionsImpl()..enableSuperMixins = true);
1126 Source source = addSource(r'''
1127 class A {
1128 toString() {
1129 return super.toString();
1130 }
1131 }
1132 class C = Object with A;''');
1133 LibraryElement library = resolve2(source);
1134 expect(library, isNotNull);
1135 CompilationUnitElement unit = library.definingCompilationUnit;
1136 expect(unit, isNotNull);
1137 ClassElement a = unit.getType('A');
1138 expect(a.isValidMixin, isTrue);
1139 assertNoErrors(source);
1140 verify([source]);
1141 }
1142
1143 void test_isValidMixin_valid() {
1144 Source source = addSource('''
1145 class A {}
1146 class C = Object with A;''');
1147 LibraryElement library = resolve2(source);
1148 expect(library, isNotNull);
1149 CompilationUnitElement unit = library.definingCompilationUnit;
1150 expect(unit, isNotNull);
1151 ClassElement a = unit.getType('A');
1152 expect(a.isValidMixin, isTrue);
1153 assertNoErrors(source);
1154 verify([source]);
1155 }
1156
1157 void test_isValidMixin_valid_withSuperMixins() {
1158 resetWithOptions(new AnalysisOptionsImpl()..enableSuperMixins = true);
1159 Source source = addSource('''
1160 class A {}
1161 class C = Object with A;''');
1162 LibraryElement library = resolve2(source);
1163 expect(library, isNotNull);
1164 CompilationUnitElement unit = library.definingCompilationUnit;
1165 expect(unit, isNotNull);
1166 ClassElement a = unit.getType('A');
1167 expect(a.isValidMixin, isTrue);
1168 assertNoErrors(source);
1169 verify([source]);
1170 }
1171
1172 void test_labels_switch() {
1173 Source source = addSource(r'''
1174 void doSwitch(int target) {
1175 switch (target) {
1176 l0: case 0:
1177 continue l1;
1178 l1: case 1:
1179 continue l0;
1180 default:
1181 continue l1;
1182 }
1183 }''');
1184 LibraryElement library = resolve2(source);
1185 expect(library, isNotNull);
1186 assertNoErrors(source);
1187 verify([source]);
1188 }
1189
1190 void test_localVariable_types_invoked() {
1191 Source source = addSource(r'''
1192 const A = null;
1193 main() {
1194 var myVar = (int p) => 'foo';
1195 myVar(42);
1196 }''');
1197 LibraryElement library = resolve2(source);
1198 expect(library, isNotNull);
1199 CompilationUnit unit =
1200 analysisContext.resolveCompilationUnit(source, library);
1201 expect(unit, isNotNull);
1202 List<bool> found = [false];
1203 List<CaughtException> thrownException = new List<CaughtException>(1);
1204 unit.accept(new _SimpleResolverTest_localVariable_types_invoked(
1205 this, found, thrownException));
1206 if (thrownException[0] != null) {
1207 throw new AnalysisException(
1208 "Exception", new CaughtException(thrownException[0], null));
1209 }
1210 expect(found[0], isTrue);
1211 }
1212
1213 void test_metadata_class() {
1214 Source source = addSource(r'''
1215 const A = null;
1216 @A class C<A> {}''');
1217 LibraryElement library = resolve2(source);
1218 expect(library, isNotNull);
1219 CompilationUnitElement unitElement = library.definingCompilationUnit;
1220 expect(unitElement, isNotNull);
1221 List<ClassElement> classes = unitElement.types;
1222 expect(classes, hasLength(1));
1223 List<ElementAnnotation> annotations = classes[0].metadata;
1224 expect(annotations, hasLength(1));
1225 assertNoErrors(source);
1226 verify([source]);
1227 CompilationUnit unit = resolveCompilationUnit(source, library);
1228 NodeList<CompilationUnitMember> declarations = unit.declarations;
1229 expect(declarations, hasLength(2));
1230 Element expectedElement = (declarations[0] as TopLevelVariableDeclaration)
1231 .variables
1232 .variables[0]
1233 .name
1234 .staticElement;
1235 EngineTestCase.assertInstanceOf((obj) => obj is PropertyInducingElement,
1236 PropertyInducingElement, expectedElement);
1237 expectedElement = (expectedElement as PropertyInducingElement).getter;
1238 Element actualElement =
1239 (declarations[1] as ClassDeclaration).metadata[0].name.staticElement;
1240 expect(actualElement, same(expectedElement));
1241 }
1242
1243 void test_metadata_field() {
1244 Source source = addSource(r'''
1245 const A = null;
1246 class C {
1247 @A int f;
1248 }''');
1249 LibraryElement library = resolve2(source);
1250 expect(library, isNotNull);
1251 CompilationUnitElement unit = library.definingCompilationUnit;
1252 expect(unit, isNotNull);
1253 List<ClassElement> classes = unit.types;
1254 expect(classes, hasLength(1));
1255 FieldElement field = classes[0].fields[0];
1256 List<ElementAnnotation> annotations = field.metadata;
1257 expect(annotations, hasLength(1));
1258 assertNoErrors(source);
1259 verify([source]);
1260 }
1261
1262 void test_metadata_fieldFormalParameter() {
1263 Source source = addSource(r'''
1264 const A = null;
1265 class C {
1266 int f;
1267 C(@A this.f);
1268 }''');
1269 LibraryElement library = resolve2(source);
1270 expect(library, isNotNull);
1271 CompilationUnitElement unit = library.definingCompilationUnit;
1272 expect(unit, isNotNull);
1273 List<ClassElement> classes = unit.types;
1274 expect(classes, hasLength(1));
1275 List<ConstructorElement> constructors = classes[0].constructors;
1276 expect(constructors, hasLength(1));
1277 List<ParameterElement> parameters = constructors[0].parameters;
1278 expect(parameters, hasLength(1));
1279 List<ElementAnnotation> annotations = parameters[0].metadata;
1280 expect(annotations, hasLength(1));
1281 assertNoErrors(source);
1282 verify([source]);
1283 }
1284
1285 void test_metadata_function() {
1286 Source source = addSource(r'''
1287 const A = null;
1288 @A f() {}''');
1289 LibraryElement library = resolve2(source);
1290 expect(library, isNotNull);
1291 CompilationUnitElement unit = library.definingCompilationUnit;
1292 expect(unit, isNotNull);
1293 List<FunctionElement> functions = unit.functions;
1294 expect(functions, hasLength(1));
1295 List<ElementAnnotation> annotations = functions[0].metadata;
1296 expect(annotations, hasLength(1));
1297 assertNoErrors(source);
1298 verify([source]);
1299 }
1300
1301 void test_metadata_functionTypedParameter() {
1302 Source source = addSource(r'''
1303 const A = null;
1304 f(@A int p(int x)) {}''');
1305 LibraryElement library = resolve2(source);
1306 expect(library, isNotNull);
1307 CompilationUnitElement unit = library.definingCompilationUnit;
1308 expect(unit, isNotNull);
1309 List<FunctionElement> functions = unit.functions;
1310 expect(functions, hasLength(1));
1311 List<ParameterElement> parameters = functions[0].parameters;
1312 expect(parameters, hasLength(1));
1313 List<ElementAnnotation> annotations1 = parameters[0].metadata;
1314 expect(annotations1, hasLength(1));
1315 assertNoErrors(source);
1316 verify([source]);
1317 }
1318
1319 void test_metadata_libraryDirective() {
1320 Source source = addSource(r'''
1321 @A library lib;
1322 const A = null;''');
1323 LibraryElement library = resolve2(source);
1324 expect(library, isNotNull);
1325 List<ElementAnnotation> annotations = library.metadata;
1326 expect(annotations, hasLength(1));
1327 assertNoErrors(source);
1328 verify([source]);
1329 }
1330
1331 void test_metadata_method() {
1332 Source source = addSource(r'''
1333 const A = null;
1334 class C {
1335 @A void m() {}
1336 }''');
1337 LibraryElement library = resolve2(source);
1338 expect(library, isNotNull);
1339 CompilationUnitElement unit = library.definingCompilationUnit;
1340 expect(unit, isNotNull);
1341 List<ClassElement> classes = unit.types;
1342 expect(classes, hasLength(1));
1343 MethodElement method = classes[0].methods[0];
1344 List<ElementAnnotation> annotations = method.metadata;
1345 expect(annotations, hasLength(1));
1346 assertNoErrors(source);
1347 verify([source]);
1348 }
1349
1350 void test_metadata_namedParameter() {
1351 Source source = addSource(r'''
1352 const A = null;
1353 f({@A int p : 0}) {}''');
1354 LibraryElement library = resolve2(source);
1355 expect(library, isNotNull);
1356 CompilationUnitElement unit = library.definingCompilationUnit;
1357 expect(unit, isNotNull);
1358 List<FunctionElement> functions = unit.functions;
1359 expect(functions, hasLength(1));
1360 List<ParameterElement> parameters = functions[0].parameters;
1361 expect(parameters, hasLength(1));
1362 List<ElementAnnotation> annotations1 = parameters[0].metadata;
1363 expect(annotations1, hasLength(1));
1364 assertNoErrors(source);
1365 verify([source]);
1366 }
1367
1368 void test_metadata_positionalParameter() {
1369 Source source = addSource(r'''
1370 const A = null;
1371 f([@A int p = 0]) {}''');
1372 LibraryElement library = resolve2(source);
1373 expect(library, isNotNull);
1374 CompilationUnitElement unit = library.definingCompilationUnit;
1375 expect(unit, isNotNull);
1376 List<FunctionElement> functions = unit.functions;
1377 expect(functions, hasLength(1));
1378 List<ParameterElement> parameters = functions[0].parameters;
1379 expect(parameters, hasLength(1));
1380 List<ElementAnnotation> annotations1 = parameters[0].metadata;
1381 expect(annotations1, hasLength(1));
1382 assertNoErrors(source);
1383 verify([source]);
1384 }
1385
1386 void test_metadata_simpleParameter() {
1387 Source source = addSource(r'''
1388 const A = null;
1389 f(@A p1, @A int p2) {}''');
1390 LibraryElement library = resolve2(source);
1391 expect(library, isNotNull);
1392 CompilationUnitElement unit = library.definingCompilationUnit;
1393 expect(unit, isNotNull);
1394 List<FunctionElement> functions = unit.functions;
1395 expect(functions, hasLength(1));
1396 List<ParameterElement> parameters = functions[0].parameters;
1397 expect(parameters, hasLength(2));
1398 List<ElementAnnotation> annotations1 = parameters[0].metadata;
1399 expect(annotations1, hasLength(1));
1400 List<ElementAnnotation> annotations2 = parameters[1].metadata;
1401 expect(annotations2, hasLength(1));
1402 assertNoErrors(source);
1403 verify([source]);
1404 }
1405
1406 void test_metadata_typedef() {
1407 Source source = addSource(r'''
1408 const A = null;
1409 @A typedef F<A>();''');
1410 LibraryElement library = resolve2(source);
1411 expect(library, isNotNull);
1412 CompilationUnitElement unitElement = library.definingCompilationUnit;
1413 expect(unitElement, isNotNull);
1414 List<FunctionTypeAliasElement> aliases = unitElement.functionTypeAliases;
1415 expect(aliases, hasLength(1));
1416 List<ElementAnnotation> annotations = aliases[0].metadata;
1417 expect(annotations, hasLength(1));
1418 assertNoErrors(source);
1419 verify([source]);
1420 CompilationUnit unit = resolveCompilationUnit(source, library);
1421 NodeList<CompilationUnitMember> declarations = unit.declarations;
1422 expect(declarations, hasLength(2));
1423 Element expectedElement = (declarations[0] as TopLevelVariableDeclaration)
1424 .variables
1425 .variables[0]
1426 .name
1427 .staticElement;
1428 EngineTestCase.assertInstanceOf((obj) => obj is PropertyInducingElement,
1429 PropertyInducingElement, expectedElement);
1430 expectedElement = (expectedElement as PropertyInducingElement).getter;
1431 Element actualElement =
1432 (declarations[1] as FunctionTypeAlias).metadata[0].name.staticElement;
1433 expect(actualElement, same(expectedElement));
1434 }
1435
1436 void test_method_fromMixin() {
1437 Source source = addSource(r'''
1438 class B {
1439 bar() => 1;
1440 }
1441 class A {
1442 foo() => 2;
1443 }
1444
1445 class C extends B with A {
1446 bar() => super.bar();
1447 foo() => super.foo();
1448 }''');
1449 computeLibrarySourceErrors(source);
1450 assertNoErrors(source);
1451 verify([source]);
1452 }
1453
1454 void test_method_fromMixins() {
1455 Source source = addSource('''
1456 class B {}
1457 class M1 {
1458 void f() {}
1459 }
1460 class M2 {
1461 void f() {}
1462 }
1463 class C extends B with M1, M2 {}
1464 void main() {
1465 new C().f();
1466 }
1467 ''');
1468 LibraryElement library = resolve2(source);
1469 assertNoErrors(source);
1470 verify([source]);
1471 // Verify that the "f" in "new C().f()" refers to the "f" defined in M2.
1472 FunctionDeclaration main =
1473 library.definingCompilationUnit.functions[0].computeNode();
1474 BlockFunctionBody body = main.functionExpression.body;
1475 ExpressionStatement stmt = body.block.statements[0];
1476 MethodInvocation expr = stmt.expression;
1477 expect(expr.methodName.staticElement.enclosingElement.name, 'M2');
1478 }
1479
1480 void test_method_fromMixins_bare_identifier() {
1481 Source source = addSource('''
1482 class B {}
1483 class M1 {
1484 void f() {}
1485 }
1486 class M2 {
1487 void f() {}
1488 }
1489 class C extends B with M1, M2 {
1490 void g() {
1491 f();
1492 }
1493 }
1494 ''');
1495 LibraryElement library = resolve2(source);
1496 assertNoErrors(source);
1497 verify([source]);
1498 // Verify that the call to f() in C.g() refers to the method defined in M2.
1499 ClassElement classC = library.definingCompilationUnit.types[3];
1500 MethodDeclaration g = classC.getMethod('g').computeNode();
1501 BlockFunctionBody body = g.body;
1502 ExpressionStatement stmt = body.block.statements[0];
1503 MethodInvocation invocation = stmt.expression;
1504 SimpleIdentifier methodName = invocation.methodName;
1505 expect(methodName.staticElement.enclosingElement.name, 'M2');
1506 }
1507
1508 void test_method_fromMixins_invked_from_outside_class() {
1509 Source source = addSource('''
1510 class B {}
1511 class M1 {
1512 void f() {}
1513 }
1514 class M2 {
1515 void f() {}
1516 }
1517 class C extends B with M1, M2 {}
1518 void main() {
1519 new C().f();
1520 }
1521 ''');
1522 LibraryElement library = resolve2(source);
1523 assertNoErrors(source);
1524 verify([source]);
1525 // Verify that the call to f() in "new C().f()" refers to the method
1526 // defined in M2.
1527 FunctionDeclaration main =
1528 library.definingCompilationUnit.functions[0].computeNode();
1529 BlockFunctionBody body = main.functionExpression.body;
1530 ExpressionStatement stmt = body.block.statements[0];
1531 MethodInvocation invocation = stmt.expression;
1532 expect(invocation.methodName.staticElement.enclosingElement.name, 'M2');
1533 }
1534
1535 void test_method_fromSuperclassMixin() {
1536 Source source = addSource(r'''
1537 class A {
1538 void m1() {}
1539 }
1540 class B extends Object with A {
1541 }
1542 class C extends B {
1543 }
1544 f(C c) {
1545 c.m1();
1546 }''');
1547 computeLibrarySourceErrors(source);
1548 assertNoErrors(source);
1549 verify([source]);
1550 }
1551
1552 void test_methodCascades() {
1553 Source source = addSource(r'''
1554 class A {
1555 void m1() {}
1556 void m2() {}
1557 void m() {
1558 A a = new A();
1559 a..m1()
1560 ..m2();
1561 }
1562 }''');
1563 computeLibrarySourceErrors(source);
1564 assertNoErrors(source);
1565 verify([source]);
1566 }
1567
1568 void test_methodCascades_withSetter() {
1569 Source source = addSource(r'''
1570 class A {
1571 String name;
1572 void m1() {}
1573 void m2() {}
1574 void m() {
1575 A a = new A();
1576 a..m1()
1577 ..name = 'name'
1578 ..m2();
1579 }
1580 }''');
1581 computeLibrarySourceErrors(source);
1582 // failing with error code: INVOCATION_OF_NON_FUNCTION
1583 assertNoErrors(source);
1584 verify([source]);
1585 }
1586
1587 void test_resolveAgainstNull() {
1588 Source source = addSource(r'''
1589 f(var p) {
1590 return null == p;
1591 }''');
1592 computeLibrarySourceErrors(source);
1593 assertNoErrors(source);
1594 }
1595
1596 void test_setter_fromMixins_bare_identifier() {
1597 Source source = addSource('''
1598 class B {}
1599 class M1 {
1600 set x(value) {}
1601 }
1602 class M2 {
1603 set x(value) {}
1604 }
1605 class C extends B with M1, M2 {
1606 void f() {
1607 x = 1;
1608 }
1609 }
1610 ''');
1611 LibraryElement library = resolve2(source);
1612 assertNoErrors(source);
1613 verify([source]);
1614 // Verify that the setter for "x" in C.f() refers to the setter defined in
1615 // M2.
1616 ClassElement classC = library.definingCompilationUnit.types[3];
1617 MethodDeclaration f = classC.getMethod('f').computeNode();
1618 BlockFunctionBody body = f.body;
1619 ExpressionStatement stmt = body.block.statements[0];
1620 AssignmentExpression assignment = stmt.expression;
1621 SimpleIdentifier leftHandSide = assignment.leftHandSide;
1622 expect(leftHandSide.staticElement.enclosingElement.name, 'M2');
1623 }
1624
1625 void test_setter_fromMixins_property_access() {
1626 Source source = addSource('''
1627 class B {}
1628 class M1 {
1629 set x(value) {}
1630 }
1631 class M2 {
1632 set x(value) {}
1633 }
1634 class C extends B with M1, M2 {}
1635 void main() {
1636 new C().x = 1;
1637 }
1638 ''');
1639 LibraryElement library = resolve2(source);
1640 assertNoErrors(source);
1641 verify([source]);
1642 // Verify that the setter for "x" in "new C().x" refers to the setter
1643 // defined in M2.
1644 FunctionDeclaration main =
1645 library.definingCompilationUnit.functions[0].computeNode();
1646 BlockFunctionBody body = main.functionExpression.body;
1647 ExpressionStatement stmt = body.block.statements[0];
1648 AssignmentExpression assignment = stmt.expression;
1649 PropertyAccess propertyAccess = assignment.leftHandSide;
1650 expect(
1651 propertyAccess.propertyName.staticElement.enclosingElement.name, 'M2');
1652 }
1653
1654 void test_setter_inherited() {
1655 Source source = addSource(r'''
1656 class A {
1657 int get x => 0;
1658 set x(int p) {}
1659 }
1660 class B extends A {
1661 int get x => super.x == null ? 0 : super.x;
1662 int f() => x = 1;
1663 }''');
1664 computeLibrarySourceErrors(source);
1665 assertNoErrors(source);
1666 verify([source]);
1667 }
1668
1669 void test_setter_static() {
1670 Source source = addSource(r'''
1671 set s(x) {
1672 }
1673
1674 main() {
1675 s = 123;
1676 }''');
1677 computeLibrarySourceErrors(source);
1678 assertNoErrors(source);
1679 verify([source]);
1680 }
1681
1682 /**
1683 * Resolve the given source and verify that the arguments in a specific method invocation were
1684 * correctly resolved.
1685 *
1686 * The source is expected to be source for a compilation unit, the first decla ration is expected
1687 * to be a class, the first member of which is expected to be a method with a block body, and the
1688 * first statement in the body is expected to be an expression statement whose expression is a
1689 * method invocation. It is the arguments to that method invocation that are t ested. The method
1690 * invocation can contain errors.
1691 *
1692 * The arguments were resolved correctly if the number of expressions in the l ist matches the
1693 * length of the array of indices and if, for each index in the array of indic es, the parameter to
1694 * which the argument expression was resolved is the parameter in the invoked method's list of
1695 * parameters at that index. Arguments that should not be resolved to a parame ter because of an
1696 * error can be denoted by including a negative index in the array of indices.
1697 *
1698 * @param source the source to be resolved
1699 * @param indices the array of indices used to associate arguments with parame ters
1700 * @throws Exception if the source could not be resolved or if the structure o f the source is not
1701 * valid
1702 */
1703 void _validateArgumentResolution(Source source, List<int> indices) {
1704 LibraryElement library = resolve2(source);
1705 expect(library, isNotNull);
1706 ClassElement classElement = library.definingCompilationUnit.types[0];
1707 List<ParameterElement> parameters = classElement.methods[1].parameters;
1708 CompilationUnit unit = resolveCompilationUnit(source, library);
1709 expect(unit, isNotNull);
1710 ClassDeclaration classDeclaration =
1711 unit.declarations[0] as ClassDeclaration;
1712 MethodDeclaration methodDeclaration =
1713 classDeclaration.members[0] as MethodDeclaration;
1714 Block block = (methodDeclaration.body as BlockFunctionBody).block;
1715 ExpressionStatement statement = block.statements[0] as ExpressionStatement;
1716 MethodInvocation invocation = statement.expression as MethodInvocation;
1717 NodeList<Expression> arguments = invocation.argumentList.arguments;
1718 int argumentCount = arguments.length;
1719 expect(argumentCount, indices.length);
1720 for (int i = 0; i < argumentCount; i++) {
1721 Expression argument = arguments[i];
1722 ParameterElement element = argument.staticParameterElement;
1723 int index = indices[i];
1724 if (index < 0) {
1725 expect(element, isNull);
1726 } else {
1727 expect(element, same(parameters[index]));
1728 }
1729 }
1730 }
1731 }
1732
1733 class _SimpleResolverTest_localVariable_types_invoked
1734 extends RecursiveAstVisitor<Object> {
1735 final SimpleResolverTest test;
1736
1737 List<bool> found;
1738
1739 List<CaughtException> thrownException;
1740
1741 _SimpleResolverTest_localVariable_types_invoked(
1742 this.test, this.found, this.thrownException)
1743 : super();
1744
1745 @override
1746 Object visitSimpleIdentifier(SimpleIdentifier node) {
1747 if (node.name == "myVar" && node.parent is MethodInvocation) {
1748 try {
1749 found[0] = true;
1750 // check static type
1751 DartType staticType = node.staticType;
1752 expect(staticType, same(test.typeProvider.dynamicType));
1753 // check propagated type
1754 FunctionType propagatedType = node.propagatedType as FunctionType;
1755 expect(propagatedType.returnType, test.typeProvider.stringType);
1756 } on AnalysisException catch (e, stackTrace) {
1757 thrownException[0] = new CaughtException(e, stackTrace);
1758 }
1759 }
1760 return null;
1761 }
1762 }
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698