[BUGFIX] Avoid reflection for public property injection
[Packages/TYPO3.CMS.git] / typo3 / sysext / extbase / Tests / Unit / Object / Container / ContainerTest.php
1 <?php
2 namespace TYPO3\CMS\Extbase\Tests\Unit\Object\Container;
3
4 /*
5 * This file is part of the TYPO3 CMS project.
6 *
7 * It is free software; you can redistribute it and/or modify it under
8 * the terms of the GNU General Public License, either version 2
9 * of the License, or any later version.
10 *
11 * For the full copyright and license information, please read the
12 * LICENSE.txt file that was distributed with this source code.
13 *
14 * The TYPO3 project - inspiring people to share!
15 */
16 use Psr\Log\LoggerInterface;
17 use TYPO3\CMS\Core\Log\Logger;
18 use TYPO3\CMS\Extbase\Object\Container\Container;
19 use TYPO3\CMS\Extbase\Object\Exception;
20 use TYPO3\CMS\Extbase\Object\Exception\CannotBuildObjectException;
21 use TYPO3\CMS\Extbase\Reflection\Exception\UnknownClassException;
22 use TYPO3\CMS\Extbase\Tests\Unit\Object\Container\Fixtures\ArgumentTestClassForPublicPropertyInjection;
23 use TYPO3\CMS\Extbase\Tests\Unit\Object\Container\Fixtures\ProtectedPropertyInjectClass;
24 use TYPO3\CMS\Extbase\Tests\Unit\Object\Container\Fixtures\PublicPropertyInjectClass;
25
26 /**
27 * Test case
28 */
29 class ContainerTest extends \TYPO3\TestingFramework\Core\Unit\UnitTestCase
30 {
31 /**
32 * @var \TYPO3\CMS\Extbase\Object\Container\Container
33 */
34 protected $container;
35
36 /**
37 * @var LoggerInterface|\PHPUnit_Framework_MockObject_MockObject
38 */
39 protected $logger;
40
41 /**
42 * @var \TYPO3\CMS\Extbase\Object\Container\ClassInfo
43 */
44 protected $cachedClassInfo;
45
46 protected function setUp()
47 {
48 // The mocked cache will always indicate that he has nothing in the cache to force that we get the real class info
49 $mockedCache = $this->getMockBuilder(\TYPO3\CMS\Extbase\Object\Container\ClassInfoCache::class)
50 ->setMethods(['get', 'set', 'has'])
51 ->getMock();
52 $mockedCache->expects($this->any())->method('get')->will($this->returnValue(false));
53 $mockedCache->expects($this->never())->method('has');
54
55 $this->logger = $this->getMockBuilder(Logger::class)
56 ->setMethods(['notice'])
57 ->disableOriginalConstructor()
58 ->getMock();
59
60 $this->container = $this->getMockBuilder(\TYPO3\CMS\Extbase\Object\Container\Container::class)
61 ->setMethods(['getLogger', 'getClassInfoCache'])
62 ->getMock();
63 $this->container->expects($this->any())->method('getClassInfoCache')->will($this->returnValue($mockedCache));
64 $this->container->expects($this->any())->method('getLogger')->will($this->returnValue($this->logger));
65 }
66
67 /**
68 * @test
69 */
70 public function getInstanceReturnsInstanceOfSimpleClass()
71 {
72 $object = $this->container->getInstance('t3lib_object_tests_c');
73 $this->assertInstanceOf('t3lib_object_tests_c', $object);
74 }
75
76 /**
77 * @test
78 */
79 public function getInstanceReturnsInstanceOfSimpleNamespacedClass()
80 {
81 $object = $this->container->getInstance(\TYPO3\CMS\Extbase\Tests\Unit\Object\Container\Fixtures\NamespacedClass::class);
82 $this->assertInstanceOf(\TYPO3\CMS\Extbase\Tests\Unit\Object\Container\Fixtures\NamespacedClass::class, $object);
83 }
84
85 /**
86 * @test
87 */
88 public function getInstanceReturnsInstanceOfAClassWithConstructorInjection()
89 {
90 $object = $this->container->getInstance('t3lib_object_tests_b');
91 $this->assertInstanceOf('t3lib_object_tests_b', $object);
92 $this->assertInstanceOf('t3lib_object_tests_c', $object->c);
93 }
94
95 /**
96 * @test
97 */
98 public function getInstanceReturnsInstanceOfAClassWithTwoLevelDependency()
99 {
100 $object = $this->container->getInstance('t3lib_object_tests_a');
101 $this->assertInstanceOf('t3lib_object_tests_a', $object);
102 $this->assertInstanceOf('t3lib_object_tests_c', $object->b->c);
103 }
104
105 /**
106 * @test
107 */
108 public function getInstanceReturnsInstanceOfAClassWithMixedSimpleTypeAndConstructorInjection()
109 {
110 $object = $this->container->getInstance('t3lib_object_tests_amixed_array');
111 $this->assertInstanceOf('t3lib_object_tests_amixed_array', $object);
112 $this->assertEquals(['some' => 'default'], $object->myvalue);
113 }
114
115 /**
116 * @test
117 */
118 public function getInstanceReturnsInstanceOfAClassWithMixedSimpleTypeAndConstructorInjectionWithNullDefaultValue()
119 {
120 $object = $this->container->getInstance('t3lib_object_tests_amixed_null');
121 $this->assertInstanceOf('t3lib_object_tests_amixed_null', $object);
122 $this->assertNull($object->myvalue);
123 }
124
125 /**
126 * @test
127 */
128 public function getInstanceThrowsExceptionWhenTryingToInstanciateASingletonWithConstructorParameters()
129 {
130 $this->expectException(Exception::class);
131 $this->expectExceptionCode(1292858051);
132 $this->container->getInstance('t3lib_object_tests_amixed_array_singleton', ['somevalue']);
133 }
134
135 /**
136 * @test
137 */
138 public function getInstanceReturnsInstanceOfAClassWithConstructorInjectionAndDefaultConstructorParameters()
139 {
140 $object = $this->container->getInstance('t3lib_object_tests_amixed_array');
141 $this->assertInstanceOf('t3lib_object_tests_b', $object->b);
142 $this->assertInstanceOf('t3lib_object_tests_c', $object->c);
143 $this->assertEquals(['some' => 'default'], $object->myvalue);
144 }
145
146 /**
147 * @test
148 */
149 public function getInstancePassesGivenParameterToTheNewObject()
150 {
151 $mockObject = $this->createMock('t3lib_object_tests_c');
152 $object = $this->container->getInstance('t3lib_object_tests_a', [$mockObject]);
153 $this->assertInstanceOf('t3lib_object_tests_a', $object);
154 $this->assertSame($mockObject, $object->c);
155 }
156
157 /**
158 * @test
159 */
160 public function getInstanceReturnsAFreshInstanceIfObjectIsNoSingleton()
161 {
162 $object1 = $this->container->getInstance('t3lib_object_tests_a');
163 $object2 = $this->container->getInstance('t3lib_object_tests_a');
164 $this->assertNotSame($object1, $object2);
165 }
166
167 /**
168 * @test
169 */
170 public function getInstanceReturnsSameInstanceInstanceIfObjectIsSingleton()
171 {
172 $object1 = $this->container->getInstance('t3lib_object_tests_singleton');
173 $object2 = $this->container->getInstance('t3lib_object_tests_singleton');
174 $this->assertSame($object1, $object2);
175 }
176
177 /**
178 * @test
179 */
180 public function getInstanceThrowsExceptionIfPrototypeObjectsWiredViaConstructorInjectionContainCyclicDependencies()
181 {
182 $this->expectException(CannotBuildObjectException::class);
183 $this->expectExceptionCode(1295611406);
184 $this->container->getInstance('t3lib_object_tests_cyclic1WithSetterDependency');
185 }
186
187 /**
188 * @test
189 */
190 public function getInstanceThrowsExceptionIfPrototypeObjectsWiredViaSetterInjectionContainCyclicDependencies()
191 {
192 $this->expectException(CannotBuildObjectException::class);
193 $this->expectExceptionCode(1295611406);
194 $this->container->getInstance('t3lib_object_tests_cyclic1');
195 }
196
197 /**
198 * @test
199 */
200 public function getInstanceThrowsExceptionIfClassWasNotFound()
201 {
202 $this->expectException(UnknownClassException::class);
203 $this->expectExceptionCode(1278450972);
204 $this->container->getInstance('nonextistingclass_bla');
205 }
206
207 /**
208 * @test
209 */
210 public function getInstanceInitializesObjects()
211 {
212 $instance = $this->container->getInstance('t3lib_object_tests_initializable');
213 $this->assertTrue($instance->isInitialized());
214 }
215
216 /**
217 * @test
218 */
219 public function getEmptyObjectReturnsInstanceOfSimpleClass()
220 {
221 $object = $this->container->getEmptyObject('t3lib_object_tests_c');
222 $this->assertInstanceOf('t3lib_object_tests_c', $object);
223 }
224
225 /**
226 * @test
227 */
228 public function getEmptyObjectReturnsInstanceOfClassImplementingSerializable()
229 {
230 $object = $this->container->getEmptyObject('t3lib_object_tests_serializable');
231 $this->assertInstanceOf('t3lib_object_tests_serializable', $object);
232 }
233
234 /**
235 * @test
236 */
237 public function getEmptyObjectInitializesObjects()
238 {
239 $object = $this->container->getEmptyObject('t3lib_object_tests_initializable');
240 $this->assertTrue($object->isInitialized());
241 }
242
243 /**
244 * @test
245 */
246 public function test_canGetChildClass()
247 {
248 $object = $this->container->getInstance('t3lib_object_tests_b_child');
249 $this->assertInstanceOf('t3lib_object_tests_b_child', $object);
250 }
251
252 /**
253 * @test
254 */
255 public function test_canInjectInterfaceInClass()
256 {
257 $this->container->registerImplementation('t3lib_object_tests_someinterface', 't3lib_object_tests_someimplementation');
258 $object = $this->container->getInstance('t3lib_object_tests_needsinterface');
259 $this->assertInstanceOf('t3lib_object_tests_needsinterface', $object);
260 $this->assertInstanceOf('t3lib_object_tests_someinterface', $object->dependency);
261 $this->assertInstanceOf('t3lib_object_tests_someimplementation', $object->dependency);
262 }
263
264 /**
265 * @test
266 */
267 public function test_canBuildCyclicDependenciesOfSingletonsWithSetter()
268 {
269 $object = $this->container->getInstance('t3lib_object_tests_resolveablecyclic1');
270 $this->assertInstanceOf('t3lib_object_tests_resolveablecyclic1', $object);
271 $this->assertInstanceOf('t3lib_object_tests_resolveablecyclic1', $object->o2->o3->o1);
272 }
273
274 /**
275 * @test
276 */
277 public function singletonWhichRequiresPrototypeViaSetterInjectionWorksAndAddsDebugMessage()
278 {
279 $this->logger->expects($this->once())->method('notice')->with('The singleton "t3lib_object_singletonNeedsPrototype" needs a prototype in "injectDependency". This is often a bad code smell; often you rather want to inject a singleton.');
280 $object = $this->container->getInstance('t3lib_object_singletonNeedsPrototype');
281 $this->assertInstanceOf('t3lib_object_prototype', $object->dependency);
282 }
283
284 /**
285 * @test
286 */
287 public function singletonWhichRequiresSingletonViaSetterInjectionWorks()
288 {
289 $this->logger->expects($this->never())->method('notice');
290 $object = $this->container->getInstance('t3lib_object_singletonNeedsSingleton');
291 $this->assertInstanceOf('t3lib_object_singleton', $object->dependency);
292 }
293
294 /**
295 * @test
296 */
297 public function prototypeWhichRequiresPrototypeViaSetterInjectionWorks()
298 {
299 $this->logger->expects($this->never())->method('notice');
300 $object = $this->container->getInstance('t3lib_object_prototypeNeedsPrototype');
301 $this->assertInstanceOf('t3lib_object_prototype', $object->dependency);
302 }
303
304 /**
305 * @test
306 */
307 public function prototypeWhichRequiresSingletonViaSetterInjectionWorks()
308 {
309 $this->logger->expects($this->never())->method('notice');
310 $object = $this->container->getInstance('t3lib_object_prototypeNeedsSingleton');
311 $this->assertInstanceOf('t3lib_object_singleton', $object->dependency);
312 }
313
314 /**
315 * @test
316 */
317 public function singletonWhichRequiresPrototypeViaConstructorInjectionWorksAndAddsDebugMessage()
318 {
319 $this->logger->expects($this->once())->method('notice')->with('The singleton "t3lib_object_singletonNeedsPrototypeInConstructor" needs a prototype in the constructor. This is often a bad code smell; often you rather want to inject a singleton.');
320 $object = $this->container->getInstance('t3lib_object_singletonNeedsPrototypeInConstructor');
321 $this->assertInstanceOf('t3lib_object_prototype', $object->dependency);
322 }
323
324 /**
325 * @test
326 */
327 public function singletonWhichRequiresSingletonViaConstructorInjectionWorks()
328 {
329 $this->logger->expects($this->never())->method('notice');
330 $object = $this->container->getInstance('t3lib_object_singletonNeedsSingletonInConstructor');
331 $this->assertInstanceOf('t3lib_object_singleton', $object->dependency);
332 }
333
334 /**
335 * @test
336 */
337 public function prototypeWhichRequiresPrototypeViaConstructorInjectionWorks()
338 {
339 $this->logger->expects($this->never())->method('notice');
340 $object = $this->container->getInstance('t3lib_object_prototypeNeedsPrototypeInConstructor');
341 $this->assertInstanceOf('t3lib_object_prototype', $object->dependency);
342 }
343
344 /**
345 * @test
346 */
347 public function prototypeWhichRequiresSingletonViaConstructorInjectionWorks()
348 {
349 $this->logger->expects($this->never())->method('notice');
350 $object = $this->container->getInstance('t3lib_object_prototypeNeedsSingletonInConstructor');
351 $this->assertInstanceOf('t3lib_object_singleton', $object->dependency);
352 }
353
354 /**
355 * @test
356 */
357 public function isSingletonReturnsTrueForSingletonInstancesAndFalseForPrototypes()
358 {
359 $this->assertTrue($this->container->isSingleton(\TYPO3\CMS\Extbase\Object\Container\Container::class));
360 $this->assertFalse($this->container->isSingleton(\TYPO3\CMS\Extbase\Core\Bootstrap::class));
361 }
362
363 /**
364 * @test
365 */
366 public function isPrototypeReturnsFalseForSingletonInstancesAndTrueForPrototypes()
367 {
368 $this->assertFalse($this->container->isPrototype(\TYPO3\CMS\Extbase\Object\Container\Container::class));
369 $this->assertTrue($this->container->isPrototype(\TYPO3\CMS\Extbase\Core\Bootstrap::class));
370 }
371
372 /************************************************
373 * Test regarding constructor argument injection
374 ************************************************/
375
376 /**
377 * test class SimpleTypeConstructorArgument
378 * @test
379 */
380 public function getInstanceGivesSimpleConstructorArgumentToClassInstance()
381 {
382 $object = $this->container->getInstance(
383 \TYPO3\CMS\Extbase\Tests\Unit\Object\Container\Fixtures\SimpleTypeConstructorArgument::class,
384 [true]
385 );
386 $this->assertTrue($object->foo);
387 }
388
389 /**
390 * test class SimpleTypeConstructorArgument
391 * @test
392 */
393 public function getInstanceDoesNotInfluenceSimpleTypeConstructorArgumentIfNotGiven()
394 {
395 $object = $this->container->getInstance(
396 \TYPO3\CMS\Extbase\Tests\Unit\Object\Container\Fixtures\SimpleTypeConstructorArgument::class
397 );
398 $this->assertFalse($object->foo);
399 }
400
401 /**
402 * test class MandatoryConstructorArgument
403 * @test
404 */
405 public function getInstanceGivesExistingConstructorArgumentToClassInstance()
406 {
407 $argumentTestClass = new Fixtures\ArgumentTestClass();
408 $object = $this->container->getInstance(
409 \TYPO3\CMS\Extbase\Tests\Unit\Object\Container\Fixtures\MandatoryConstructorArgument::class,
410 [$argumentTestClass]
411 );
412 $this->assertInstanceOf(
413 \TYPO3\CMS\Extbase\Tests\Unit\Object\Container\Fixtures\MandatoryConstructorArgument::class,
414 $object
415 );
416 $this->assertSame($argumentTestClass, $object->argumentTestClass);
417 }
418
419 /**
420 * test class MandatoryConstructorArgument
421 * @test
422 */
423 public function getInstanceInjectsNewInstanceOfClassToClassIfArgumentIsMandatory()
424 {
425 $object = $this->container->getInstance(
426 \TYPO3\CMS\Extbase\Tests\Unit\Object\Container\Fixtures\MandatoryConstructorArgument::class
427 );
428 $this->assertInstanceOf(
429 \TYPO3\CMS\Extbase\Tests\Unit\Object\Container\Fixtures\MandatoryConstructorArgument::class,
430 $object
431 );
432 $this->assertInstanceOf(
433 \TYPO3\CMS\Extbase\Tests\Unit\Object\Container\Fixtures\ArgumentTestClass::class,
434 $object->argumentTestClass
435 );
436 }
437
438 /**
439 * test class OptionalConstructorArgument
440 * @test
441 */
442 public function getInstanceDoesNotInjectAnOptionalArgumentIfNotGiven()
443 {
444 $object = $this->container->getInstance(
445 \TYPO3\CMS\Extbase\Tests\Unit\Object\Container\Fixtures\OptionalConstructorArgument::class
446 );
447 $this->assertInstanceOf(
448 \TYPO3\CMS\Extbase\Tests\Unit\Object\Container\Fixtures\OptionalConstructorArgument::class,
449 $object
450 );
451 $this->assertNull($object->argumentTestClass);
452 }
453
454 /**
455 * test class OptionalConstructorArgument
456 * @test
457 */
458 public function getInstanceDoesNotInjectAnOptionalArgumentIfGivenArgumentIsNull()
459 {
460 $object = $this->container->getInstance(
461 \TYPO3\CMS\Extbase\Tests\Unit\Object\Container\Fixtures\OptionalConstructorArgument::class,
462 [null]
463 );
464 $this->assertInstanceOf(
465 \TYPO3\CMS\Extbase\Tests\Unit\Object\Container\Fixtures\OptionalConstructorArgument::class,
466 $object
467 );
468 $this->assertNull($object->argumentTestClass);
469 }
470
471 /**
472 * test class OptionalConstructorArgument
473 * @test
474 */
475 public function getInstanceGivesExistingConstructorArgumentToClassInstanceIfArgumentIsGiven()
476 {
477 $argumentTestClass = new Fixtures\ArgumentTestClass();
478 $object = $this->container->getInstance(
479 \TYPO3\CMS\Extbase\Tests\Unit\Object\Container\Fixtures\OptionalConstructorArgument::class,
480 [$argumentTestClass]
481 );
482 $this->assertInstanceOf(
483 \TYPO3\CMS\Extbase\Tests\Unit\Object\Container\Fixtures\OptionalConstructorArgument::class,
484 $object
485 );
486 $this->assertSame($argumentTestClass, $object->argumentTestClass);
487 }
488
489 /**
490 * test class MandatoryConstructorArgumentTwo
491 * @test
492 */
493 public function getInstanceGivesTwoArgumentsToClassConstructor()
494 {
495 $firstArgument = new Fixtures\ArgumentTestClass();
496 $secondArgument = new Fixtures\ArgumentTestClass();
497 $object = $this->container->getInstance(
498 \TYPO3\CMS\Extbase\Tests\Unit\Object\Container\Fixtures\MandatoryConstructorArgumentTwo::class,
499 [$firstArgument, $secondArgument]
500 );
501 $this->assertInstanceOf(
502 \TYPO3\CMS\Extbase\Tests\Unit\Object\Container\Fixtures\MandatoryConstructorArgumentTwo::class,
503 $object
504 );
505 $this->assertSame(
506 $firstArgument,
507 $object->argumentTestClass
508 );
509 $this->assertSame(
510 $secondArgument,
511 $object->argumentTestClassTwo
512 );
513 }
514
515 /**
516 * test class MandatoryConstructorArgumentTwo
517 * @test
518 */
519 public function getInstanceInjectsTwoMandatoryArguments()
520 {
521 $object = $this->container->getInstance(
522 \TYPO3\CMS\Extbase\Tests\Unit\Object\Container\Fixtures\MandatoryConstructorArgumentTwo::class
523 );
524 $this->assertInstanceOf(
525 \TYPO3\CMS\Extbase\Tests\Unit\Object\Container\Fixtures\MandatoryConstructorArgumentTwo::class,
526 $object
527 );
528 $this->assertInstanceOf(
529 \TYPO3\CMS\Extbase\Tests\Unit\Object\Container\Fixtures\ArgumentTestClass::class,
530 $object->argumentTestClass
531 );
532 $this->assertInstanceOf(
533 \TYPO3\CMS\Extbase\Tests\Unit\Object\Container\Fixtures\ArgumentTestClass::class,
534 $object->argumentTestClassTwo
535 );
536 $this->assertNotSame(
537 $object->argumentTestClass,
538 $object->argumentTestClassTwo
539 );
540 }
541
542 /**
543 * test class MandatoryConstructorArgumentTwo
544 * @test
545 */
546 public function getInstanceInjectsSecondMandatoryArgumentIfFirstIsGiven()
547 {
548 $firstArgument = new Fixtures\ArgumentTestClass();
549 $object = $this->container->getInstance(
550 \TYPO3\CMS\Extbase\Tests\Unit\Object\Container\Fixtures\MandatoryConstructorArgumentTwo::class,
551 [$firstArgument]
552 );
553 $this->assertInstanceOf(
554 \TYPO3\CMS\Extbase\Tests\Unit\Object\Container\Fixtures\MandatoryConstructorArgumentTwo::class,
555 $object
556 );
557 $this->assertSame(
558 $firstArgument,
559 $object->argumentTestClass
560 );
561 $this->assertInstanceOf(
562 \TYPO3\CMS\Extbase\Tests\Unit\Object\Container\Fixtures\ArgumentTestClass::class,
563 $object->argumentTestClassTwo
564 );
565 $this->assertNotSame(
566 $object->argumentTestClass,
567 $object->argumentTestClassTwo
568 );
569 }
570
571 /**
572 * test class MandatoryConstructorArgumentTwo
573 * @test
574 */
575 public function getInstanceInjectsFirstMandatoryArgumentIfSecondIsGiven()
576 {
577 $secondArgument = new Fixtures\ArgumentTestClass();
578 $object = $this->container->getInstance(
579 \TYPO3\CMS\Extbase\Tests\Unit\Object\Container\Fixtures\MandatoryConstructorArgumentTwo::class,
580 [null, $secondArgument]
581 );
582 $this->assertInstanceOf(
583 \TYPO3\CMS\Extbase\Tests\Unit\Object\Container\Fixtures\MandatoryConstructorArgumentTwo::class,
584 $object
585 );
586 $this->assertInstanceOf(
587 \TYPO3\CMS\Extbase\Tests\Unit\Object\Container\Fixtures\ArgumentTestClass::class,
588 $object->argumentTestClass
589 );
590 $this->assertInstanceOf(
591 \TYPO3\CMS\Extbase\Tests\Unit\Object\Container\Fixtures\ArgumentTestClass::class,
592 $object->argumentTestClassTwo
593 );
594 $this->assertSame(
595 $secondArgument,
596 $object->argumentTestClassTwo
597 );
598 $this->assertNotSame(
599 $object->argumentTestClass,
600 $object->argumentTestClassTwo
601 );
602 }
603
604 /**
605 * test class TwoConstructorArgumentsSecondOptional
606 * @test
607 */
608 public function getInstanceGivesTwoArgumentsToClassConstructorIfSecondIsOptional()
609 {
610 $firstArgument = new Fixtures\ArgumentTestClass();
611 $secondArgument = new Fixtures\ArgumentTestClass();
612 $object = $this->container->getInstance(
613 \TYPO3\CMS\Extbase\Tests\Unit\Object\Container\Fixtures\TwoConstructorArgumentsSecondOptional::class,
614 [$firstArgument, $secondArgument]
615 );
616 $this->assertInstanceOf(
617 \TYPO3\CMS\Extbase\Tests\Unit\Object\Container\Fixtures\TwoConstructorArgumentsSecondOptional::class,
618 $object
619 );
620 $this->assertSame(
621 $firstArgument,
622 $object->argumentTestClass
623 );
624 $this->assertSame(
625 $secondArgument,
626 $object->argumentTestClassTwo
627 );
628 }
629
630 /**
631 * test class TwoConstructorArgumentsSecondOptional
632 * @test
633 */
634 public function getInstanceInjectsFirstMandatoryArgumentIfSecondIsOptionalAndNoneAreGiven()
635 {
636 $object = $this->container->getInstance(
637 \TYPO3\CMS\Extbase\Tests\Unit\Object\Container\Fixtures\TwoConstructorArgumentsSecondOptional::class
638 );
639 $this->assertInstanceOf(
640 \TYPO3\CMS\Extbase\Tests\Unit\Object\Container\Fixtures\TwoConstructorArgumentsSecondOptional::class,
641 $object
642 );
643 $this->assertInstanceOf(
644 \TYPO3\CMS\Extbase\Tests\Unit\Object\Container\Fixtures\ArgumentTestClass::class,
645 $object->argumentTestClass
646 );
647 $this->assertNull($object->argumentTestClassTwo);
648 }
649
650 /**
651 * test class TwoConstructorArgumentsSecondOptional
652 * @test
653 */
654 public function getInstanceInjectsFirstMandatoryArgumentIfSecondIsOptionalAndBothAreGivenAsNull()
655 {
656 $object = $this->container->getInstance(
657 \TYPO3\CMS\Extbase\Tests\Unit\Object\Container\Fixtures\TwoConstructorArgumentsSecondOptional::class,
658 [null, null]
659 );
660 $this->assertInstanceOf(
661 \TYPO3\CMS\Extbase\Tests\Unit\Object\Container\Fixtures\TwoConstructorArgumentsSecondOptional::class,
662 $object
663 );
664 $this->assertInstanceOf(
665 \TYPO3\CMS\Extbase\Tests\Unit\Object\Container\Fixtures\ArgumentTestClass::class,
666 $object->argumentTestClass
667 );
668 $this->assertNull($object->argumentTestClassTwo);
669 }
670
671 /**
672 * test class TwoConstructorArgumentsSecondOptional
673 * @test
674 */
675 public function getInstanceGivesFirstArgumentToConstructorIfSecondIsOptionalAndFirstIsGiven()
676 {
677 $firstArgument = new Fixtures\ArgumentTestClass();
678 $object = $this->container->getInstance(
679 \TYPO3\CMS\Extbase\Tests\Unit\Object\Container\Fixtures\TwoConstructorArgumentsSecondOptional::class,
680 [$firstArgument]
681 );
682 $this->assertInstanceOf(
683 \TYPO3\CMS\Extbase\Tests\Unit\Object\Container\Fixtures\TwoConstructorArgumentsSecondOptional::class,
684 $object
685 );
686 $this->assertSame(
687 $firstArgument,
688 $object->argumentTestClass
689 );
690 $this->assertNull($object->argumentTestClassTwo);
691 }
692
693 /**
694 * test class TwoConstructorArgumentsSecondOptional
695 * @test
696 */
697 public function getInstanceGivesFirstArgumentToConstructorIfSecondIsOptionalFirstIsGivenAndSecondIsGivenNull()
698 {
699 $firstArgument = new Fixtures\ArgumentTestClass();
700 $object = $this->container->getInstance(
701 \TYPO3\CMS\Extbase\Tests\Unit\Object\Container\Fixtures\TwoConstructorArgumentsSecondOptional::class,
702 [$firstArgument, null]
703 );
704 $this->assertInstanceOf(
705 \TYPO3\CMS\Extbase\Tests\Unit\Object\Container\Fixtures\TwoConstructorArgumentsSecondOptional::class,
706 $object
707 );
708 $this->assertSame(
709 $firstArgument,
710 $object->argumentTestClass
711 );
712 $this->assertNull($object->argumentTestClassTwo);
713 }
714
715 /**
716 * test class TwoConstructorArgumentsFirstOptional
717 *
718 * @test
719 */
720 public function getInstanceOnFirstOptionalAndSecondMandatoryInjectsSecondArgumentIfFirstIsGivenAsNull()
721 {
722 $object = $this->container->getInstance(
723 \TYPO3\CMS\Extbase\Tests\Unit\Object\Container\Fixtures\TwoConstructorArgumentsFirstOptional::class,
724 [null]
725 );
726 $this->assertInstanceOf(
727 \TYPO3\CMS\Extbase\Tests\Unit\Object\Container\Fixtures\TwoConstructorArgumentsFirstOptional::class,
728 $object
729 );
730 $this->assertInstanceOf(
731 \TYPO3\CMS\Extbase\Tests\Unit\Object\Container\Fixtures\ArgumentTestClass::class,
732 $object->argumentTestClassTwo
733 );
734 }
735
736 /**
737 * test class TwoConstructorArgumentsFirstOptional
738 * @test
739 */
740 public function getInstanceOnFirstOptionalAndSecondMandatoryGivesTwoGivenArgumentsToConstructor()
741 {
742 $first = new Fixtures\ArgumentTestClass();
743 $second = new Fixtures\ArgumentTestClass();
744 $object = $this->container->getInstance(
745 \TYPO3\CMS\Extbase\Tests\Unit\Object\Container\Fixtures\TwoConstructorArgumentsFirstOptional::class,
746 [$first, $second]
747 );
748 $this->assertInstanceOf(
749 \TYPO3\CMS\Extbase\Tests\Unit\Object\Container\Fixtures\TwoConstructorArgumentsFirstOptional::class,
750 $object
751 );
752 $this->assertSame(
753 $first,
754 $object->argumentTestClass
755 );
756 $this->assertSame(
757 $second,
758 $object->argumentTestClassTwo
759 );
760 }
761
762 /**
763 * test class TwoConstructorArgumentsFirstOptional
764 * @test
765 */
766 public function getInstanceOnFirstOptionalAndSecondMandatoryInjectsSecondArgumentIfFirstIsGiven()
767 {
768 $first = new Fixtures\ArgumentTestClass();
769 $object = $this->container->getInstance(
770 \TYPO3\CMS\Extbase\Tests\Unit\Object\Container\Fixtures\TwoConstructorArgumentsFirstOptional::class,
771 [$first]
772 );
773 $this->assertInstanceOf(
774 \TYPO3\CMS\Extbase\Tests\Unit\Object\Container\Fixtures\TwoConstructorArgumentsFirstOptional::class,
775 $object
776 );
777 $this->assertSame(
778 $first,
779 $object->argumentTestClass
780 );
781 $this->assertInstanceOf(
782 \TYPO3\CMS\Extbase\Tests\Unit\Object\Container\Fixtures\ArgumentTestClass::class,
783 $object->argumentTestClassTwo
784 );
785 $this->assertNotSame(
786 $object->argumentTestClass,
787 $object->argumentTestClassTwo
788 );
789 }
790
791 /**
792 * test class TwoConstructorArgumentsFirstOptional
793 *
794 * @test
795 */
796 public function getInstanceOnFirstOptionalAndSecondMandatoryGivesSecondArgumentAsIsIfFirstIsGivenAsNullAndSecondIsGiven()
797 {
798 $second = new Fixtures\ArgumentTestClass();
799 $object = $this->container->getInstance(
800 \TYPO3\CMS\Extbase\Tests\Unit\Object\Container\Fixtures\TwoConstructorArgumentsFirstOptional::class,
801 [null, $second]
802 );
803 $this->assertInstanceOf(
804 \TYPO3\CMS\Extbase\Tests\Unit\Object\Container\Fixtures\TwoConstructorArgumentsFirstOptional::class,
805 $object
806 );
807 $this->assertSame(
808 $second,
809 $object->argumentTestClassTwo
810 );
811 }
812
813 /**
814 * test class TwoConstructorArgumentsFirstOptional
815 *
816 * @test
817 */
818 public function getInstanceOnFirstOptionalAndSecondMandatoryInjectsSecondArgumentIfFirstIsGivenAsNullAndSecondIsNull()
819 {
820 $object = $this->container->getInstance(
821 \TYPO3\CMS\Extbase\Tests\Unit\Object\Container\Fixtures\TwoConstructorArgumentsFirstOptional::class,
822 [null, null]
823 );
824 $this->assertInstanceOf(
825 \TYPO3\CMS\Extbase\Tests\Unit\Object\Container\Fixtures\TwoConstructorArgumentsFirstOptional::class,
826 $object
827 );
828 $this->assertInstanceOf(
829 \TYPO3\CMS\Extbase\Tests\Unit\Object\Container\Fixtures\ArgumentTestClass::class,
830 $object->argumentTestClassTwo
831 );
832 }
833
834 /**
835 * test class TwoConstructorArgumentsBothOptional
836 * @test
837 */
838 public function getInstanceOnTwoOptionalGivesTwoGivenArgumentsToConstructor()
839 {
840 $first = new Fixtures\ArgumentTestClass();
841 $second = new Fixtures\ArgumentTestClass();
842 $object = $this->container->getInstance(
843 \TYPO3\CMS\Extbase\Tests\Unit\Object\Container\Fixtures\TwoConstructorArgumentsBothOptional::class,
844 [$first, $second]
845 );
846 $this->assertInstanceOf(
847 \TYPO3\CMS\Extbase\Tests\Unit\Object\Container\Fixtures\TwoConstructorArgumentsBothOptional::class,
848 $object
849 );
850 $this->assertSame(
851 $first,
852 $object->argumentTestClass
853 );
854 $this->assertSame(
855 $second,
856 $object->argumentTestClassTwo
857 );
858 }
859
860 /**
861 * test class TwoConstructorArgumentsBothOptional
862 * @test
863 */
864 public function getInstanceOnTwoOptionalGivesNoArgumentsToConstructorIfArgumentsAreNull()
865 {
866 $object = $this->container->getInstance(
867 \TYPO3\CMS\Extbase\Tests\Unit\Object\Container\Fixtures\TwoConstructorArgumentsBothOptional::class,
868 [null, null]
869 );
870 $this->assertInstanceOf(
871 \TYPO3\CMS\Extbase\Tests\Unit\Object\Container\Fixtures\TwoConstructorArgumentsBothOptional::class,
872 $object
873 );
874 $this->assertNull($object->argumentTestClass);
875 $this->assertNull($object->argumentTestClassTwo);
876 }
877
878 /**
879 * test class TwoConstructorArgumentsBothOptional
880 * @test
881 */
882 public function getInstanceOnTwoOptionalGivesNoArgumentsToConstructorIfNoneAreGiven()
883 {
884 $object = $this->container->getInstance(
885 \TYPO3\CMS\Extbase\Tests\Unit\Object\Container\Fixtures\TwoConstructorArgumentsBothOptional::class
886 );
887 $this->assertInstanceOf(
888 \TYPO3\CMS\Extbase\Tests\Unit\Object\Container\Fixtures\TwoConstructorArgumentsBothOptional::class,
889 $object
890 );
891 $this->assertNull($object->argumentTestClass);
892 $this->assertNull($object->argumentTestClassTwo);
893 }
894
895 /**
896 * test class TwoConstructorArgumentsBothOptional
897 * @test
898 */
899 public function getInstanceOnTwoOptionalGivesOneArgumentToConstructorIfFirstIsObjectAndSecondIsNotGiven()
900 {
901 $first = new Fixtures\ArgumentTestClass();
902 $object = $this->container->getInstance(
903 \TYPO3\CMS\Extbase\Tests\Unit\Object\Container\Fixtures\TwoConstructorArgumentsBothOptional::class,
904 [$first]
905 );
906 $this->assertInstanceOf(
907 \TYPO3\CMS\Extbase\Tests\Unit\Object\Container\Fixtures\TwoConstructorArgumentsBothOptional::class,
908 $object
909 );
910 $this->assertSame(
911 $first,
912 $object->argumentTestClass
913 );
914 $this->assertNull($object->argumentTestClassTwo);
915 }
916
917 /**
918 * test class TwoConstructorArgumentsBothOptional
919 * @test
920 */
921 public function getInstanceOnTwoOptionalGivesOneArgumentToConstructorIfFirstIsObjectAndSecondIsNull()
922 {
923 $first = new Fixtures\ArgumentTestClass();
924 $object = $this->container->getInstance(
925 \TYPO3\CMS\Extbase\Tests\Unit\Object\Container\Fixtures\TwoConstructorArgumentsBothOptional::class,
926 [$first, null]
927 );
928 $this->assertInstanceOf(
929 \TYPO3\CMS\Extbase\Tests\Unit\Object\Container\Fixtures\TwoConstructorArgumentsBothOptional::class,
930 $object
931 );
932 $this->assertSame(
933 $first,
934 $object->argumentTestClass
935 );
936 $this->assertNull($object->argumentTestClassTwo);
937 }
938
939 /**
940 * test class TwoConstructorArgumentsBothOptional
941 * @test
942 */
943 public function getInstanceOnTwoOptionalGivesOneArgumentToConstructorIfFirstIsNullAndSecondIsObject()
944 {
945 $second = new Fixtures\ArgumentTestClass();
946 $object = $this->container->getInstance(
947 \TYPO3\CMS\Extbase\Tests\Unit\Object\Container\Fixtures\TwoConstructorArgumentsBothOptional::class,
948 [null, $second]
949 );
950 $this->assertInstanceOf(
951 \TYPO3\CMS\Extbase\Tests\Unit\Object\Container\Fixtures\TwoConstructorArgumentsBothOptional::class,
952 $object
953 );
954 $this->assertNull($object->argumentTestClass);
955 $this->assertSame(
956 $second,
957 $object->argumentTestClassTwo
958 );
959 }
960
961 /**
962 * @test
963 */
964 public function getInstanceInjectsPublicProperties()
965 {
966 $container = new Container();
967 $object = $container->getInstance(PublicPropertyInjectClass::class);
968 self::assertInstanceOf(ArgumentTestClassForPublicPropertyInjection::class, $object->foo);
969 }
970
971 /**
972 * @test
973 */
974 public function getInstanceInjectsProtectedProperties()
975 {
976 $container = new Container();
977 $object = $container->getInstance(ProtectedPropertyInjectClass::class);
978 self::assertInstanceOf(ArgumentTestClassForPublicPropertyInjection::class, $object->getFoo());
979 }
980 }