TYPO3 CMS  TYPO3_7-6
PersistentObjectConverterTest.php
Go to the documentation of this file.
1 <?php
3 
4 /* *
5  * This script belongs to the Extbase framework. *
6  * *
7  * It is free software; you can redistribute it and/or modify it under *
8  * the terms of the GNU Lesser General Public License as published by the *
9  * Free Software Foundation, either version 3 of the License, or (at your *
10  * option) any later version. *
11  * *
12  * This script is distributed in the hope that it will be useful, but *
13  * WITHOUT ANY WARRANTY; without even the implied warranty of MERCHAN- *
14  * TABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser *
15  * General Public License for more details. *
16  * *
17  * You should have received a copy of the GNU Lesser General Public *
18  * License along with the script. *
19  * If not, see http://www.gnu.org/licenses/lgpl.html *
20  * *
21  * The TYPO3 project - inspiring people to share! *
22  * */
28 
33 {
37  protected $converter;
38 
43 
48 
52  protected $mockObjectManager;
53 
57  protected $mockContainer;
58 
64  protected function setUp()
65  {
66  $this->converter = new PersistentObjectConverter();
67  $this->mockReflectionService = $this->getMock(\TYPO3\CMS\Extbase\Reflection\ReflectionService::class);
68  $this->inject($this->converter, 'reflectionService', $this->mockReflectionService);
69 
70  $this->mockPersistenceManager = $this->getMock(\TYPO3\CMS\Extbase\Persistence\PersistenceManagerInterface::class);
71  $this->inject($this->converter, 'persistenceManager', $this->mockPersistenceManager);
72 
73  $this->mockObjectManager = $this->getMock(\TYPO3\CMS\Extbase\Object\ObjectManagerInterface::class);
74  $this->mockObjectManager->expects($this->any())
75  ->method('get')
76  ->will($this->returnCallback(function () {
77  $args = func_get_args();
78  $reflectionClass = new \ReflectionClass(array_shift($args));
79  if (empty($args)) {
80  return $reflectionClass->newInstance();
81  } else {
82  return $reflectionClass->newInstanceArgs($args);
83  }
84  }));
85  $this->inject($this->converter, 'objectManager', $this->mockObjectManager);
86 
87  $this->mockContainer = $this->getMock(\TYPO3\CMS\Extbase\Object\Container\Container::class);
88  $this->inject($this->converter, 'objectContainer', $this->mockContainer);
89  }
90 
94  public function checkMetadata()
95  {
96  $this->assertEquals(['integer', 'string', 'array'], $this->converter->getSupportedSourceTypes(), 'Source types do not match');
97  $this->assertEquals('object', $this->converter->getSupportedTargetType(), 'Target type does not match');
98  $this->assertEquals(1, $this->converter->getPriority(), 'Priority does not match');
99  }
100 
104  public function dataProviderForCanConvert()
105  {
106  return [
107  [true, false, true],
108  // is entity => can convert
109  [false, true, true],
110  // is valueobject => can convert
111  [false, false, false],
112  // is no entity and no value object => can not convert
113  ];
114  }
115 
120  public function canConvertFromReturnsTrueIfClassIsTaggedWithEntityOrValueObject($isEntity, $isValueObject, $expected)
121  {
122  $className = PersistentObjectFixture::class;
123 
124  if ($isEntity) {
125  $className = PersistentObjectEntityFixture::class;
126  } elseif ($isValueObject) {
127  $className = PersistentObjectValueObjectFixture::class;
128  }
129  $this->assertEquals($expected, $this->converter->canConvertFrom('myInputData', $className));
130  }
131 
136  {
137  $source = [
138  'k1' => 'v1',
139  '__identity' => 'someIdentity',
140  'k2' => 'v2'
141  ];
142  $expected = [
143  'k1' => 'v1',
144  'k2' => 'v2'
145  ];
146  $this->assertEquals($expected, $this->converter->getSourceChildPropertiesToBeConverted($source));
147  }
148 
153  {
154  $mockSchema = $this->getMockBuilder(\TYPO3\CMS\Extbase\Reflection\ClassSchema::class)->disableOriginalConstructor()->getMock();
155  $this->mockReflectionService->expects($this->any())->method('getClassSchema')->with('TheTargetType')->will($this->returnValue($mockSchema));
156 
157  $this->mockContainer->expects($this->any())->method('getImplementationClassName')->will($this->returnValue('TheTargetType'));
158  $mockSchema->expects($this->any())->method('hasProperty')->with('thePropertyName')->will($this->returnValue(true));
159  $mockSchema->expects($this->any())->method('getProperty')->with('thePropertyName')->will($this->returnValue([
160  'type' => 'TheTypeOfSubObject',
161  'elementType' => null
162  ]));
163  $configuration = $this->buildConfiguration([]);
164  $this->assertEquals('TheTypeOfSubObject', $this->converter->getTypeOfChildProperty('TheTargetType', 'thePropertyName', $configuration));
165  }
166 
171  {
172  $this->mockReflectionService->expects($this->never())->method('getClassSchema');
173  $this->mockContainer->expects($this->any())->method('getImplementationClassName')->will($this->returnValue('foo'));
174 
175  $configuration = $this->buildConfiguration([]);
176  $configuration->forProperty('thePropertyName')->setTypeConverterOption(\TYPO3\CMS\Extbase\Property\TypeConverter\PersistentObjectConverter::class, PersistentObjectConverter::CONFIGURATION_TARGET_TYPE, 'Foo\Bar');
177  $this->assertEquals('Foo\Bar', $this->converter->getTypeOfChildProperty('foo', 'thePropertyName', $configuration));
178  }
179 
184  {
185  $identifier = '17';
186  $object = new \stdClass();
187 
188  $this->mockPersistenceManager->expects($this->any())->method('getObjectByIdentifier')->with($identifier)->will($this->returnValue($object));
189  $this->assertSame($object, $this->converter->convertFrom($identifier, 'MySpecialType'));
190  }
191 
196  {
197  $identifier = '17';
198  $object = new \stdClass();
199 
200  $this->mockPersistenceManager->expects($this->any())->method('getObjectByIdentifier')->with($identifier)->will($this->returnValue($object));
201  $this->assertSame($object, $this->converter->convertFrom($identifier, 'MySpecialType'));
202  }
203 
208  {
209  $identifier = '12345';
210  $object = new \stdClass();
211 
212  $source = [
213  '__identity' => $identifier
214  ];
215  $this->mockPersistenceManager->expects($this->any())->method('getObjectByIdentifier')->with($identifier)->will($this->returnValue($object));
216  $this->assertSame($object, $this->converter->convertFrom($source, 'MySpecialType'));
217  }
218 
224  {
225  $identifier = '12345';
226  $object = new \stdClass();
227  $object->someProperty = 'asdf';
228 
229  $source = [
230  '__identity' => $identifier,
231  'foo' => 'bar'
232  ];
233  $this->mockPersistenceManager->expects($this->any())->method('getObjectByIdentifier')->with($identifier)->will($this->returnValue($object));
234  $this->converter->convertFrom($source, 'MySpecialType');
235  }
236 
241  protected function buildConfiguration($typeConverterOptions)
242  {
243  $configuration = new \TYPO3\CMS\Extbase\Property\PropertyMappingConfiguration();
244  $configuration->setTypeConverterOptions(\TYPO3\CMS\Extbase\Property\TypeConverter\PersistentObjectConverter::class, $typeConverterOptions);
245  return $configuration;
246  }
247 
253  public function setupMockQuery($numberOfResults, $howOftenIsGetFirstCalled)
254  {
255  $mockClassSchema = $this->getMock(\TYPO3\CMS\Extbase\Reflection\ClassSchema::class, [], ['Dummy']);
256  $mockClassSchema->expects($this->any())->method('getIdentityProperties')->will($this->returnValue(['key1' => 'someType']));
257  $this->mockReflectionService->expects($this->any())->method('getClassSchema')->with('SomeType')->will($this->returnValue($mockClassSchema));
258 
259  $mockConstraint = $this->getMockBuilder(\TYPO3\CMS\Extbase\Persistence\Generic\Qom\Comparison::class)->disableOriginalConstructor()->getMock();
260 
261  $mockObject = new \stdClass();
262  $mockQuery = $this->getMock(\TYPO3\CMS\Extbase\Persistence\QueryInterface::class);
263  $mockQueryResult = $this->getMock(\TYPO3\CMS\Extbase\Persistence\QueryResultInterface::class);
264  $mockQueryResult->expects($this->any())->method('count')->will($this->returnValue($numberOfResults));
265  $mockQueryResult->expects($howOftenIsGetFirstCalled)->method('getFirst')->will($this->returnValue($mockObject));
266  $mockQuery->expects($this->any())->method('equals')->with('key1', 'value1')->will($this->returnValue($mockConstraint));
267  $mockQuery->expects($this->any())->method('matching')->with($mockConstraint)->will($this->returnValue($mockQuery));
268  $mockQuery->expects($this->any())->method('execute')->will($this->returnValue($mockQueryResult));
269 
270  $this->mockPersistenceManager->expects($this->any())->method('createQueryForType')->with('SomeType')->will($this->returnValue($mockQuery));
271 
272  return $mockObject;
273  }
274 
280  {
281  $this->setupMockQuery(0, $this->never());
282  $this->mockReflectionService->expects($this->never())->method('getClassSchema');
283 
284  $source = [
285  '__identity' => 123
286  ];
287  $actual = $this->converter->convertFrom($source, 'SomeType');
288  $this->assertNull($actual);
289  }
290 
296  {
297  $this->setupMockQuery(2, $this->never());
298 
299  $source = [
300  '__identity' => 666
301  ];
302  $this->mockPersistenceManager->expects($this->any())->method('getObjectByIdentifier')->with(666)->will($this->throwException(new \TYPO3\CMS\Extbase\Property\Exception\DuplicateObjectException));
303  $this->converter->convertFrom($source, 'SomeType');
304  }
305 
311  {
312  $source = [
313  'foo' => 'bar'
314  ];
315  $this->converter->convertFrom($source, 'MySpecialType');
316  }
317 
322  {
323  $source = [
324  'propertyX' => 'bar'
325  ];
326  $convertedChildProperties = [
327  'property1' => 'bar'
328  ];
329  $expectedObject = new \TYPO3\CMS\Extbase\Tests\Fixture\ClassWithSetters();
330  $expectedObject->property1 = 'bar';
331 
332  $this->mockReflectionService->expects($this->any())->method('getMethodParameters')->with(\TYPO3\CMS\Extbase\Tests\Fixture\ClassWithSetters::class, '__construct')->will($this->throwException(new \ReflectionException()));
333  $this->mockObjectManager->expects($this->any())->method('getClassNameByObjectName')->with(\TYPO3\CMS\Extbase\Tests\Fixture\ClassWithSetters::class)->will($this->returnValue(\TYPO3\CMS\Extbase\Tests\Fixture\ClassWithSetters::class));
335  $result = $this->converter->convertFrom($source, \TYPO3\CMS\Extbase\Tests\Fixture\ClassWithSetters::class, $convertedChildProperties, $configuration);
336  $this->assertEquals($expectedObject, $result);
337  }
338 
344  {
345  $source = [
346  'propertyX' => 'bar'
347  ];
348  $object = new \TYPO3\CMS\Extbase\Tests\Fixture\ClassWithSetters();
349  $convertedChildProperties = [
350  'propertyNotExisting' => 'bar'
351  ];
352  $this->mockObjectManager->expects($this->any())->method('get')->with(\TYPO3\CMS\Extbase\Tests\Fixture\ClassWithSetters::class)->will($this->returnValue($object));
353  $this->mockReflectionService->expects($this->any())->method('getMethodParameters')->with(\TYPO3\CMS\Extbase\Tests\Fixture\ClassWithSetters::class, '__construct')->will($this->returnValue([]));
355  $result = $this->converter->convertFrom($source, \TYPO3\CMS\Extbase\Tests\Fixture\ClassWithSetters::class, $convertedChildProperties, $configuration);
356  $this->assertSame($object, $result);
357  }
358 
363  {
364  $source = [
365  'propertyX' => 'bar'
366  ];
367  $convertedChildProperties = [
368  'property1' => 'param1',
369  'property2' => 'bar'
370  ];
371  $expectedObject = new \TYPO3\CMS\Extbase\Tests\Fixture\ClassWithSettersAndConstructor('param1');
372  $expectedObject->setProperty2('bar');
373 
374  $this->mockReflectionService
375  ->expects($this->any())
376  ->method('getMethodParameters')
377  ->with(\TYPO3\CMS\Extbase\Tests\Fixture\ClassWithSettersAndConstructor::class, '__construct')
378  ->will($this->returnValue([
379  'property1' => ['optional' => false]
380  ]));
381  $this->mockReflectionService
382  ->expects($this->any())
383  ->method('hasMethod')
384  ->with(\TYPO3\CMS\Extbase\Tests\Fixture\ClassWithSettersAndConstructor::class, '__construct')
385  ->will($this->returnValue(true));
386  $this->mockObjectManager->expects($this->any())->method('getClassNameByObjectName')->with(\TYPO3\CMS\Extbase\Tests\Fixture\ClassWithSettersAndConstructor::class)->will($this->returnValue(\TYPO3\CMS\Extbase\Tests\Fixture\ClassWithSettersAndConstructor::class));
387  $this->mockContainer->expects($this->any())->method('getImplementationClassName')->will($this->returnValue(\TYPO3\CMS\Extbase\Tests\Fixture\ClassWithSettersAndConstructor::class));
389  $result = $this->converter->convertFrom($source, \TYPO3\CMS\Extbase\Tests\Fixture\ClassWithSettersAndConstructor::class, $convertedChildProperties, $configuration);
390  $this->assertEquals($expectedObject, $result);
391  $this->assertEquals('bar', $expectedObject->getProperty2());
392  }
393 
398  {
399  $source = [
400  'propertyX' => 'bar'
401  ];
402  $expectedObject = new \TYPO3\CMS\Extbase\Tests\Fixture\ClassWithSettersAndConstructor('thisIsTheDefaultValue');
403 
404  $this->mockReflectionService->expects($this->any())->method('getMethodParameters')->with(\TYPO3\CMS\Extbase\Tests\Fixture\ClassWithSettersAndConstructor::class, '__construct')->will($this->returnValue([
405  'property1' => ['optional' => true, 'defaultValue' => 'thisIsTheDefaultValue']
406  ]));
407  $this->mockReflectionService
408  ->expects($this->any())
409  ->method('hasMethod')
410  ->with(\TYPO3\CMS\Extbase\Tests\Fixture\ClassWithSettersAndConstructor::class, '__construct')
411  ->will($this->returnValue(true));
412  $this->mockObjectManager->expects($this->any())->method('getClassNameByObjectName')->with(\TYPO3\CMS\Extbase\Tests\Fixture\ClassWithSettersAndConstructor::class)->will($this->returnValue(\TYPO3\CMS\Extbase\Tests\Fixture\ClassWithSettersAndConstructor::class));
413  $this->mockContainer->expects($this->any())->method('getImplementationClassName')->will($this->returnValue(\TYPO3\CMS\Extbase\Tests\Fixture\ClassWithSettersAndConstructor::class));
415  $result = $this->converter->convertFrom($source, \TYPO3\CMS\Extbase\Tests\Fixture\ClassWithSettersAndConstructor::class, [], $configuration);
416  $this->assertEquals($expectedObject, $result);
417  }
418 
424  {
425  $source = [
426  'propertyX' => 'bar'
427  ];
428  $object = new \TYPO3\CMS\Extbase\Tests\Fixture\ClassWithSettersAndConstructor('param1');
429  $convertedChildProperties = [
430  'property2' => 'bar'
431  ];
432 
433  $this->mockReflectionService->expects($this->any())->method('getMethodParameters')->with(\TYPO3\CMS\Extbase\Tests\Fixture\ClassWithSettersAndConstructor::class, '__construct')->will($this->returnValue([
434  'property1' => ['optional' => false]
435  ]));
436  $this->mockReflectionService
437  ->expects($this->any())
438  ->method('hasMethod')
439  ->with(\TYPO3\CMS\Extbase\Tests\Fixture\ClassWithSettersAndConstructor::class, '__construct')
440  ->will($this->returnValue(true));
441  $this->mockObjectManager->expects($this->any())->method('getClassNameByObjectName')->with(\TYPO3\CMS\Extbase\Tests\Fixture\ClassWithSettersAndConstructor::class)->will($this->returnValue(\TYPO3\CMS\Extbase\Tests\Fixture\ClassWithSettersAndConstructor::class));
442  $this->mockContainer->expects($this->any())->method('getImplementationClassName')->will($this->returnValue(\TYPO3\CMS\Extbase\Tests\Fixture\ClassWithSettersAndConstructor::class));
444  $result = $this->converter->convertFrom($source, \TYPO3\CMS\Extbase\Tests\Fixture\ClassWithSettersAndConstructor::class, $convertedChildProperties, $configuration);
445  $this->assertSame($object, $result);
446  }
447 
452  {
453  $source = '';
454  $result = $this->converter->convertFrom($source, \TYPO3\CMS\Extbase\Tests\Fixture\ClassWithSettersAndConstructor::class);
455  $this->assertNull($result);
456  }
457 }
inject($target, $name, $dependency)