[FEATURE] Store extension configuration as plain array
[Packages/TYPO3.CMS.git] / typo3 / sysext / extensionmanager / Tests / Unit / Utility / ConfigurationUtilityTest.php
1 <?php
2 namespace TYPO3\CMS\Extensionmanager\Tests\Unit\Utility;
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
17 use TYPO3\CMS\Extensionmanager\Utility\ConfigurationUtility;
18
19 /**
20 * Configuration utility test
21 */
22 class ConfigurationUtilityTest extends \TYPO3\TestingFramework\Core\Unit\UnitTestCase
23 {
24 /**
25 * @test
26 */
27 public function getCurrentConfigurationReturnsExtensionConfigurationAsValuedConfiguration()
28 {
29 /** @var $configurationUtility ConfigurationUtility|\TYPO3\TestingFramework\Core\AccessibleObjectInterface|\PHPUnit_Framework_MockObject_MockObject */
30 $configurationUtility = $this->getMockBuilder(ConfigurationUtility::class)
31 ->setMethods(['getDefaultConfigurationFromExtConfTemplateAsValuedArray'])
32 ->getMock();
33 $configurationUtility
34 ->expects($this->once())
35 ->method('getDefaultConfigurationFromExtConfTemplateAsValuedArray')
36 ->will($this->returnValue([]));
37 $extensionKey = $this->getUniqueId('some-extension');
38
39 $currentConfiguration = [
40 'key1' => 'value1',
41 'key2.' => [
42 'subkey1' => 'value2'
43 ]
44 ];
45
46 $expected = [
47 'key1' => [
48 'value' => 'value1',
49 ],
50 'key2.subkey1' => [
51 'value' => 'value2',
52 ],
53 ];
54
55 $GLOBALS['TYPO3_CONF_VARS']['EXT']['extConf'][$extensionKey] = serialize($currentConfiguration);
56 $actual = $configurationUtility->getCurrentConfiguration($extensionKey);
57 $this->assertEquals($expected, $actual);
58 }
59
60 /**
61 * @test
62 */
63 public function getCurrentConfigurationReturnsExtensionConfigurationWithExtconfBasedConfigurationPrioritized()
64 {
65 /** @var $configurationUtility \TYPO3\CMS\Extensionmanager\Utility\ConfigurationUtility|\TYPO3\TestingFramework\Core\AccessibleObjectInterface|\PHPUnit_Framework_MockObject_MockObject */
66 $configurationUtility = $this->getMockBuilder(\TYPO3\CMS\Extensionmanager\Utility\ConfigurationUtility::class)
67 ->setMethods(['getDefaultConfigurationFromExtConfTemplateAsValuedArray'])
68 ->getMock();
69 $configurationUtility
70 ->expects($this->once())
71 ->method('getDefaultConfigurationFromExtConfTemplateAsValuedArray')
72 ->will($this->returnValue([]));
73 $extensionKey = $this->getUniqueId('some-extension');
74
75 $serializedConfiguration = [
76 'key1' => 'value1',
77 'key2.' => [
78 'subkey1' => 'somevalue'
79 ]
80 ];
81 $currentExtconfConfiguration = [
82 'key1' => 'value1',
83 'key2.' => [
84 'subkey1' => 'overwritten'
85 ]
86 ];
87
88 $expected = [
89 'key1' => [
90 'value' => 'value1',
91 ],
92 'key2.subkey1' => [
93 'value' => 'overwritten',
94 ],
95 ];
96
97 $GLOBALS['TYPO3_CONF_VARS']['EXT']['extConf'][$extensionKey] = serialize($serializedConfiguration);
98 $GLOBALS['TYPO3_CONF_VARS']['EXTCONF'][$extensionKey] = $currentExtconfConfiguration;
99 $actual = $configurationUtility->getCurrentConfiguration($extensionKey);
100 $this->assertEquals($expected, $actual);
101 }
102
103 /**
104 * @test
105 */
106 public function mergeDefaultConfigurationReturnsEmptyArrayIfNoConfigurationForExtensionExists()
107 {
108 $configurationUtility = new ConfigurationUtility();
109 $result = $configurationUtility->getCurrentConfiguration('not_existing_extension');
110 self::assertSame([], $result);
111 }
112
113 /**
114 * @test
115 */
116 public function getDefaultConfigurationFromExtConfTemplateAsValuedArrayReturnsExpectedExampleArray()
117 {
118 /** @var $configurationUtility \TYPO3\CMS\Extensionmanager\Utility\ConfigurationUtility|\TYPO3\TestingFramework\Core\AccessibleObjectInterface|\PHPUnit_Framework_MockObject_MockObject */
119 $configurationUtility = $this->getAccessibleMock(
120 \TYPO3\CMS\Extensionmanager\Utility\ConfigurationUtility::class,
121 ['getDefaultConfigurationRawString']
122 );
123 $configurationUtility
124 ->expects($this->once())
125 ->method('getDefaultConfigurationRawString')
126 ->will($this->returnValue('foo'));
127
128 $tsStyleConfig = $this->getMockBuilder(\TYPO3\CMS\Core\TypoScript\ConfigurationForm::class)->getMock();
129
130 $objectManagerMock = $this->getMockBuilder(\TYPO3\CMS\Extbase\Object\ObjectManagerInterface::class)->getMock();
131 $configurationUtility->_set('objectManager', $objectManagerMock);
132 $objectManagerMock
133 ->expects($this->once())
134 ->method('get')
135 ->with(\TYPO3\CMS\Core\TypoScript\ConfigurationForm::class)
136 ->will($this->returnValue($tsStyleConfig));
137
138 $constants = [
139 'checkConfigurationFE' => [
140 'cat' => 'basic',
141 'subcat_name' => 'enable',
142 'subcat' => 'a/enable/z',
143 'type' => 'user[TYPO3\\CMS\\Saltedpasswords\\Utility\\ExtensionManagerConfigurationUtility->checkConfigurationFrontend]',
144 'label' => 'Frontend configuration check',
145 'name' => 'checkConfigurationFE',
146 'value' => '0',
147 'default_value' => '0'
148 ],
149 'BE.forceSalted' => [
150 'cat' => 'advancedbackend',
151 'subcat' => 'x/z',
152 'type' => 'boolean',
153 'label' => 'Force salted passwords: Enforce usage of SaltedPasswords. Old MD5 hashed passwords will stop working.',
154 'name' => 'BE.forceSalted',
155 'value' => '0',
156 'default_value' => '0'
157 ]
158 ];
159 $tsStyleConfig
160 ->expects($this->once())
161 ->method('ext_initTSstyleConfig')
162 ->will($this->returnValue($constants));
163
164 $setupTsConstantEditor = [
165 'advancedbackend.' => [
166 'description' => '<span style="background:red; padding:1px 2px; color:#fff; font-weight:bold;">1</span> Install tool has hardcoded md5 hashing, enabling this setting will prevent use of a install-tool-created BE user.<br />Currently same is for changin password with user setup module unless you use pending patch!',
167 1 => 'BE.forceSalted'
168 ]
169 ];
170 $tsStyleConfig->setup['constants']['TSConstantEditor.'] = $setupTsConstantEditor;
171
172 $expected = [
173 'checkConfigurationFE' => [
174 'cat' => 'basic',
175 'subcat_name' => 'enable',
176 'subcat' => 'a/enable/z',
177 'type' => 'user[TYPO3\\CMS\\Saltedpasswords\\Utility\\ExtensionManagerConfigurationUtility->checkConfigurationFrontend]',
178 'label' => 'Frontend configuration check',
179 'name' => 'checkConfigurationFE',
180 'value' => '0',
181 'default_value' => '0',
182 'subcat_label' => 'Enable features',
183 ],
184 'BE.forceSalted' => [
185 'cat' => 'advancedbackend',
186 'subcat' => 'x/z',
187 'type' => 'boolean',
188 'label' => 'Force salted passwords: Enforce usage of SaltedPasswords. Old MD5 hashed passwords will stop working.',
189 'name' => 'BE.forceSalted',
190 'value' => '0',
191 'default_value' => '0',
192 'highlight' => 1,
193 ],
194 '__meta__' => [
195 'advancedbackend' => [
196 'highlightText' => '<span style="background:red; padding:1px 2px; color:#fff; font-weight:bold;">1</span> Install tool has hardcoded md5 hashing, enabling this setting will prevent use of a install-tool-created BE user.<br />Currently same is for changin password with user setup module unless you use pending patch!'
197 ]
198 ]
199 ];
200
201 $result = $configurationUtility->getDefaultConfigurationFromExtConfTemplateAsValuedArray($this->getUniqueId('some_extension'));
202 $this->assertEquals($expected, $result);
203 }
204
205 /**
206 * Data provider for convertValuedToNestedConfiguration
207 *
208 * @return array
209 */
210 public function convertValuedToNestedConfigurationDataProvider()
211 {
212 return [
213 'plain array' => [
214 [
215 'first' => [
216 'value' => 'value1'
217 ],
218 'second' => [
219 'value' => 'value2'
220 ]
221 ],
222 [
223 'first' => 'value1',
224 'second' => 'value2'
225 ]
226 ],
227 'nested value with 2 levels' => [
228 [
229 'first.firstSub' => [
230 'value' => 'value1'
231 ],
232 'second.secondSub' => [
233 'value' => 'value2'
234 ]
235 ],
236 [
237 'first.' => [
238 'firstSub' => 'value1'
239 ],
240 'second.' => [
241 'secondSub' => 'value2'
242 ]
243 ]
244 ],
245 'nested value with 3 levels' => [
246 [
247 'first.firstSub.firstSubSub' => [
248 'value' => 'value1'
249 ],
250 'second.secondSub.secondSubSub' => [
251 'value' => 'value2'
252 ]
253 ],
254 [
255 'first.' => [
256 'firstSub.' => [
257 'firstSubSub' => 'value1'
258 ]
259 ],
260 'second.' => [
261 'secondSub.' => [
262 'secondSubSub' => 'value2'
263 ]
264 ]
265 ]
266 ],
267 'mixed nested value with 2 levels' => [
268 [
269 'first' => [
270 'value' => 'firstValue'
271 ],
272 'first.firstSub' => [
273 'value' => 'value1'
274 ],
275 'second.secondSub' => [
276 'value' => 'value2'
277 ]
278 ],
279 [
280 'first' => 'firstValue',
281 'first.' => [
282 'firstSub' => 'value1'
283 ],
284 'second.' => [
285 'secondSub' => 'value2'
286 ]
287 ]
288 ]
289 ];
290 }
291
292 /**
293 * @test
294 * @dataProvider convertValuedToNestedConfigurationDataProvider
295 *
296 * @param array $configuration
297 * @param array $expected
298 */
299 public function convertValuedToNestedConfiguration(array $configuration, array $expected)
300 {
301 /** @var $subject \TYPO3\CMS\Extensionmanager\Utility\ConfigurationUtility|\PHPUnit_Framework_MockObject_MockObject|\TYPO3\TestingFramework\Core\AccessibleObjectInterface */
302 $subject = $this->getAccessibleMock(\TYPO3\CMS\Extensionmanager\Utility\ConfigurationUtility::class, ['dummy'], [], '', false);
303 $this->assertEquals($expected, $subject->convertValuedToNestedConfiguration($configuration));
304 }
305
306 /**
307 * Data provider for convertNestedToValuedConfiguration
308 *
309 * @return array
310 */
311 public function convertNestedToValuedConfigurationDataProvider()
312 {
313 return [
314 'plain array' => [
315 [
316 'first' => 'value1',
317 'second' => 'value2'
318 ],
319 [
320 'first' => ['value' => 'value1'],
321 'second' => ['value' => 'value2'],
322 ]
323 ],
324 'two levels' => [
325 [
326 'first.' => ['firstSub' => 'value1'],
327 'second.' => ['firstSub' => 'value2'],
328 ],
329 [
330 'first.firstSub' => ['value' => 'value1'],
331 'second.firstSub' => ['value' => 'value2'],
332 ]
333 ],
334 'three levels' => [
335 [
336 'first.' => ['firstSub.' => ['firstSubSub' => 'value1']],
337 'second.' => ['firstSub.' => ['firstSubSub' => 'value2']]
338 ],
339 [
340 'first.firstSub.firstSubSub' => ['value' => 'value1'],
341 'second.firstSub.firstSubSub' => ['value' => 'value2'],
342 ]
343 ],
344 'mixed' => [
345 [
346 'first.' => ['firstSub' => 'value1'],
347 'second.' => ['firstSub.' => ['firstSubSub' => 'value2']],
348 'third' => 'value3'
349 ],
350 [
351 'first.firstSub' => ['value' => 'value1'],
352 'second.firstSub.firstSubSub' => ['value' => 'value2'],
353 'third' => ['value' => 'value3']
354 ]
355 ]
356 ];
357 }
358
359 /**
360 * @test
361 * @dataProvider convertNestedToValuedConfigurationDataProvider
362 *
363 * @param array $configuration
364 * @param array $expected
365 */
366 public function convertNestedToValuedConfiguration(array $configuration, array $expected)
367 {
368 /** @var $subject \TYPO3\CMS\Extensionmanager\Utility\ConfigurationUtility|\PHPUnit_Framework_MockObject_MockObject|\TYPO3\TestingFramework\Core\AccessibleObjectInterface */
369 $subject = $this->getAccessibleMock(\TYPO3\CMS\Extensionmanager\Utility\ConfigurationUtility::class, ['dummy'], [], '', false);
370 $this->assertEquals($expected, $subject->convertNestedToValuedConfiguration($configuration));
371 }
372 }