[TASK] Streamline expressionLanguage usage in core
[Packages/TYPO3.CMS.git] / typo3 / sysext / backend / Tests / UnitDeprecated / Configuration / TypoScript / ConditionMatching / ConditionMatcherTest.php
1 <?php
2 namespace TYPO3\CMS\Backend\Tests\UnitDeprecated\Configuration\TypoScript\ConditionMatching;
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 Prophecy\Argument;
18 use TYPO3\CMS\Backend\Configuration\TypoScript\ConditionMatching\ConditionMatcher;
19 use TYPO3\CMS\Backend\Tests\UnitDeprecated\Configuration\TypoScript\ConditionMatching\Fixtures\TestConditionException;
20 use TYPO3\CMS\Core\Authentication\BackendUserAuthentication;
21 use TYPO3\CMS\Core\Cache\CacheManager;
22 use TYPO3\CMS\Core\Cache\Frontend\FrontendInterface;
23 use TYPO3\CMS\Core\Context\Context;
24 use TYPO3\CMS\Core\Context\UserAspect;
25 use TYPO3\CMS\Core\Http\ServerRequest;
26 use TYPO3\CMS\Core\Log\Logger;
27 use TYPO3\CMS\Core\Package\PackageInterface;
28 use TYPO3\CMS\Core\Package\PackageManager;
29 use TYPO3\CMS\Core\Utility\GeneralUtility;
30
31 /**
32 * Testcase for class \TYPO3\CMS\Backend\Configuration\TypoScript\ConditionMatching\ConditionMatcher.
33 */
34 class ConditionMatcherTest extends \TYPO3\TestingFramework\Core\Unit\UnitTestCase
35 {
36 /**
37 * @var array
38 */
39 protected $rootline;
40
41 /**
42 * @var \TYPO3\CMS\Backend\Configuration\TypoScript\ConditionMatching\ConditionMatcher
43 */
44 protected $matchCondition;
45
46 /**
47 * @var string
48 */
49 protected $testGlobalNamespace;
50
51 /**
52 * @var string
53 */
54 protected $testTableName;
55
56 /**
57 * @var bool Reset singletons
58 */
59 protected $resetSingletonInstances = true;
60
61 /**
62 * Set up tests
63 */
64 protected function setUp()
65 {
66 $GLOBALS['TYPO3_REQUEST'] = new ServerRequest();
67 $cacheFrontendProphecy = $this->prophesize(FrontendInterface::class);
68 $cacheFrontendProphecy->has(Argument::any())->willReturn(false);
69 $cacheFrontendProphecy->set(Argument::any(), Argument::any())->willReturn(null);
70 $cacheManagerProphecy = $this->prophesize(CacheManager::class);
71 $cacheManagerProphecy->getCache('cache_core')->willReturn($cacheFrontendProphecy->reveal());
72 GeneralUtility::setSingletonInstance(CacheManager::class, $cacheManagerProphecy->reveal());
73
74 $packageManagerProphecy = $this->prophesize(PackageManager::class);
75 $corePackageProphecy = $this->prophesize(PackageInterface::class);
76 $corePackageProphecy->getPackagePath()->willReturn(__DIR__ . '/../../../../../../../sysext/core/');
77 $packageManagerProphecy->getActivePackages()->willReturn([
78 $corePackageProphecy->reveal()
79 ]);
80 GeneralUtility::setSingletonInstance(PackageManager::class, $packageManagerProphecy->reveal());
81 $this->testTableName = 'conditionMatcherTestTable';
82 $this->testGlobalNamespace = $this->getUniqueId('TEST');
83 $GLOBALS['TCA'][$this->testTableName] = ['ctrl' => []];
84 $GLOBALS[$this->testGlobalNamespace] = [];
85 $this->setUpBackend();
86 $this->matchCondition = $this->getAccessibleMock(ConditionMatcher::class, ['determineRootline'], [], '', false);
87 $this->matchCondition->method('determineRootline')->willReturn([
88 2 => ['uid' => 121, 'pid' => 111],
89 1 => ['uid' => 111, 'pid' => 101],
90 0 => ['uid' => 101, 'pid' => 0]
91 ]);
92 $this->matchCondition->__construct();
93 $loggerProphecy = $this->prophesize(Logger::class);
94 $this->matchCondition->setLogger($loggerProphecy->reveal());
95 }
96
97 /**
98 * Set up a backend
99 */
100 private function setUpBackend()
101 {
102 $this->rootline = [
103 2 => ['uid' => 121, 'pid' => 111],
104 1 => ['uid' => 111, 'pid' => 101],
105 0 => ['uid' => 101, 'pid' => 0]
106 ];
107 $GLOBALS['BE_USER'] = $this->getMockBuilder(BackendUserAuthentication::class)
108 ->setMethods(['dummy'])
109 ->disableOriginalConstructor()
110 ->getMock();
111 $GLOBALS['BE_USER']->groupList = '13,14,15';
112 $GLOBALS['BE_USER']->user['uid'] = 13;
113 $GLOBALS['BE_USER']->user['admin'] = 1;
114
115 GeneralUtility::makeInstance(Context::class)
116 ->setAspect('backend.user', new UserAspect($GLOBALS['BE_USER']));
117 }
118
119 /**
120 * Set up database mock
121 */
122 private function setUpDatabaseMockForDeterminePageId()
123 {
124 $this->matchCondition = $this->getAccessibleMock(ConditionMatcher::class, ['determineRootline', 'determinePageId'], [], '', false);
125 $this->matchCondition->method('determineRootline')->willReturn([
126 2 => ['uid' => 121, 'pid' => 111],
127 1 => ['uid' => 111, 'pid' => 101],
128 0 => ['uid' => 101, 'pid' => 0]
129 ]);
130 $this->matchCondition->__construct();
131 $loggerProphecy = $this->prophesize(Logger::class);
132 $this->matchCondition->setLogger($loggerProphecy->reveal());
133
134 $this->matchCondition->expects($this->once())->method('determinePageId')->willReturn(999);
135 }
136
137 /**
138 * Tests whether a faulty expression fails.
139 *
140 * @test
141 */
142 public function simulateDisabledMatchAllConditionsFailsOnFaultyExpression()
143 {
144 $this->assertFalse($this->matchCondition->match('[nullCondition = This expression would return FALSE in general]'));
145 }
146
147 /**
148 * Tests whether simulating positive matches for all conditions succeeds.
149 *
150 * @test
151 */
152 public function simulateEnabledMatchAllConditionsSucceeds()
153 {
154 $this->matchCondition->setSimulateMatchResult(true);
155 $this->assertTrue($this->matchCondition->match('[nullCondition = This expression would return FALSE in general]'));
156 }
157
158 /**
159 * Tests whether simulating positive matches for specific conditions succeeds.
160 *
161 * @test
162 */
163 public function simulateEnabledMatchSpecificConditionsSucceeds()
164 {
165 $testCondition = '[' . $this->getUniqueId('test') . ' = Any condition to simulate a positive match]';
166 $this->matchCondition->setSimulateMatchConditions([$testCondition]);
167 $this->assertTrue($this->matchCondition->match($testCondition));
168 }
169
170 /**
171 * Tests whether the language comparison matches.
172 *
173 * @test
174 */
175 public function languageConditionMatchesSingleLanguageExpression()
176 {
177 $_SERVER['HTTP_ACCEPT_LANGUAGE'] = 'de-de,de;q=0.8,en-us;q=0.5,en;q=0.3';
178 $this->assertTrue($this->matchCondition->match('[language = *de*]'));
179 $this->assertTrue($this->matchCondition->match('[language = *de-de*]'));
180 }
181
182 /**
183 * Tests whether the language comparison matches.
184 *
185 * @test
186 */
187 public function languageConditionMatchesMultipleLanguagesExpression()
188 {
189 $_SERVER['HTTP_ACCEPT_LANGUAGE'] = 'de-de,de;q=0.8,en-us;q=0.5,en;q=0.3';
190 $this->assertTrue($this->matchCondition->match('[language = *en*,*de*]'));
191 $this->assertTrue($this->matchCondition->match('[language = *en-us*,*de-de*]'));
192 }
193
194 /**
195 * Tests whether the language comparison matches.
196 *
197 * @test
198 */
199 public function languageConditionMatchesCompleteLanguagesExpression()
200 {
201 $_SERVER['HTTP_ACCEPT_LANGUAGE'] = 'de-de,de;q=0.8,en-us;q=0.5,en;q=0.3';
202 $this->assertTrue($this->matchCondition->match('[language = de-de,de;q=0.8,en-us;q=0.5,en;q=0.3]'));
203 }
204
205 /**
206 * Tests whether usergroup comparison matches.
207 *
208 * @test
209 */
210 public function usergroupConditionMatchesSingleGroupId()
211 {
212 $this->assertTrue($this->matchCondition->match('[usergroup = 13]'));
213 }
214
215 /**
216 * Tests whether usergroup comparison matches.
217 *
218 * @test
219 */
220 public function usergroupConditionMatchesMultipleUserGroupId()
221 {
222 $this->assertTrue($this->matchCondition->match('[usergroup = 999,15,14,13]'));
223 }
224
225 /**
226 * Tests whether user comparison matches.
227 *
228 * @test
229 */
230 public function loginUserConditionMatchesAnyLoggedInUser()
231 {
232 $this->assertTrue($this->matchCondition->match('[loginUser = *]'));
233 }
234
235 /**
236 * Tests whether user comparison matches.
237 *
238 * @test
239 */
240 public function loginUserConditionMatchesSingleLoggedInUser()
241 {
242 $this->assertTrue($this->matchCondition->match('[loginUser = 13]'));
243 }
244
245 /**
246 * Tests whether user comparison matches.
247 *
248 * @test
249 */
250 public function loginUserConditionDoesNotMatchSingleLoggedInUser()
251 {
252 $GLOBALS['BE_USER']->user['uid'] = 13;
253 $this->assertFalse($this->matchCondition->match('[loginUser = 999]'));
254 }
255
256 /**
257 * Tests whether user comparison matches.
258 *
259 * @test
260 */
261 public function loginUserConditionMatchesMultipleLoggedInUsers()
262 {
263 $this->assertTrue($this->matchCondition->match('[loginUser = 999,13]'));
264 }
265
266 /**
267 * Tests whether checkinf for an admin user matches
268 *
269 * @test
270 */
271 public function adminUserConditionMatchesAdminUser()
272 {
273 $this->assertTrue($this->matchCondition->match('[adminUser = 1]'));
274 }
275
276 /**
277 * Tests whether checkinf for an admin user matches
278 *
279 * @test
280 */
281 public function adminUserConditionMatchesRegularUser()
282 {
283 $GLOBALS['BE_USER']->user['uid'] = 14;
284 $GLOBALS['BE_USER']->user['admin'] = 0;
285 $this->assertTrue($this->matchCondition->match('[adminUser = 0]'));
286 }
287
288 /**
289 * Tests whether checkinf for an admin user matches
290 *
291 * @test
292 */
293 public function adminUserConditionDoesNotMatchRegularUser()
294 {
295 $GLOBALS['BE_USER']->user['uid'] = 14;
296 $GLOBALS['BE_USER']->user['admin'] = 0;
297 $this->assertFalse($this->matchCondition->match('[adminUser = 1]'));
298 }
299
300 /**
301 * Tests whether numerical comparison matches.
302 *
303 * @test
304 */
305 public function globalVarConditionMatchesOnEqualExpression()
306 {
307 $this->assertTrue($this->matchCondition->match('[globalVar = LIT:10 = 10]'), '1');
308 $this->assertTrue($this->matchCondition->match('[globalVar = LIT:10.1 = 10.1]'), '2');
309 $this->assertTrue($this->matchCondition->match('[globalVar = LIT:10 == 10]'), '3');
310 $this->assertTrue($this->matchCondition->match('[globalVar = LIT:10.1 == 10.1]'), '4');
311 $this->assertTrue($this->matchCondition->match('[globalVar = LIT:0 = 0]'), '5');
312 $this->assertTrue($this->matchCondition->match('[globalVar = LIT:0 == 0]'), '6');
313 }
314
315 /**
316 * Tests whether numerical comparison matches.
317 *
318 * @test
319 */
320 public function globalVarConditionMatchesOnEqualExpressionWithMultipleValues()
321 {
322 $this->assertTrue($this->matchCondition->match('[globalVar = LIT:10 = 10|20|30]'));
323 $this->assertTrue($this->matchCondition->match('[globalVar = LIT:10.1 = 10.1|20.2|30.3]'));
324 $this->assertTrue($this->matchCondition->match('[globalVar = LIT:20 = 10|20|30]'));
325 $this->assertTrue($this->matchCondition->match('[globalVar = LIT:20.2 = 10.1|20.2|30.3]'));
326 $this->assertTrue($this->matchCondition->match('[globalVar = LIT:10 == 10|20|30]'));
327 $this->assertTrue($this->matchCondition->match('[globalVar = LIT:10.1 == 10.1|20.2|30.3]'));
328 $this->assertTrue($this->matchCondition->match('[globalVar = LIT:20 == 10|20|30]'));
329 $this->assertTrue($this->matchCondition->match('[globalVar = LIT:20.2 == 10.1|20.2|30.3]'));
330 }
331
332 /**
333 * Tests whether numerical comparison matches.
334 *
335 * @test
336 */
337 public function globalVarConditionMatchesOnNotEqualExpression()
338 {
339 $this->assertTrue($this->matchCondition->match('[globalVar = LIT:10 != 20]'));
340 $this->assertTrue($this->matchCondition->match('[globalVar = LIT:10.1 != 10.2]'));
341 $this->assertTrue($this->matchCondition->match('[globalVar = LIT:0 != 1]'));
342 }
343
344 /**
345 * Tests whether numerical comparison does not match.
346 *
347 * @test
348 */
349 public function globalVarConditionDoesNotMatchOnNotEqualExpression()
350 {
351 $this->assertFalse($this->matchCondition->match('[globalVar = LIT:10 != 10]'));
352 }
353
354 /**
355 * Tests whether numerical comparison matches.
356 *
357 * @test
358 */
359 public function globalVarConditionMatchesOnNotEqualExpressionWithMultipleValues()
360 {
361 $this->assertTrue($this->matchCondition->match('[globalVar = LIT:10 != 20|30]'));
362 $this->assertTrue($this->matchCondition->match('[globalVar = LIT:10.1 != 10.2|20.3]'));
363 }
364
365 /**
366 * Tests whether numerical comparison matches.
367 *
368 * @test
369 */
370 public function globalVarConditionMatchesOnLowerThanExpression()
371 {
372 $this->assertTrue($this->matchCondition->match('[globalVar = LIT:10 < 20]'));
373 $this->assertTrue($this->matchCondition->match('[globalVar = LIT:10.1 < 10.2]'));
374 $this->assertTrue($this->matchCondition->match('[globalVar = LIT:0 < 1]'));
375 }
376
377 /**
378 * Tests whether numerical comparison matches.
379 *
380 * @test
381 */
382 public function globalVarConditionMatchesOnLowerThanOrEqualExpression()
383 {
384 $this->assertTrue($this->matchCondition->match('[globalVar = LIT:10 <= 10]'));
385 $this->assertTrue($this->matchCondition->match('[globalVar = LIT:10 <= 20]'));
386 $this->assertTrue($this->matchCondition->match('[globalVar = LIT:10.1 <= 10.1]'));
387 $this->assertTrue($this->matchCondition->match('[globalVar = LIT:10.1 <= 10.2]'));
388 }
389
390 /**
391 * Tests whether numerical comparison matches.
392 *
393 * @test
394 */
395 public function globalVarConditionMatchesOnGreaterThanExpression()
396 {
397 $this->assertTrue($this->matchCondition->match('[globalVar = LIT:20 > 10]'));
398 $this->assertTrue($this->matchCondition->match('[globalVar = LIT:10.2 > 10.1]'));
399 $this->assertTrue($this->matchCondition->match('[globalVar = LIT:1 > 0]'));
400 }
401
402 /**
403 * Tests whether numerical comparison matches.
404 *
405 * @test
406 */
407 public function globalVarConditionMatchesOnGreaterThanOrEqualExpression()
408 {
409 $this->assertTrue($this->matchCondition->match('[globalVar = LIT:10 >= 10]'));
410 $this->assertTrue($this->matchCondition->match('[globalVar = LIT:20 >= 10]'));
411 $this->assertTrue($this->matchCondition->match('[globalVar = LIT:10.1 >= 10.1]'));
412 $this->assertTrue($this->matchCondition->match('[globalVar = LIT:10.2 >= 10.1]'));
413 }
414
415 /**
416 * Tests whether numerical comparison matches.
417 *
418 * @test
419 */
420 public function globalVarConditionMatchesOnEmptyExpressionWithNoValueSet()
421 {
422 $testKey = $this->getUniqueId('test');
423 $this->assertTrue($this->matchCondition->match('[globalVar = GP:' . $testKey . '=]'));
424 $this->assertTrue($this->matchCondition->match('[globalVar = GP:' . $testKey . ' = ]'));
425 }
426
427 /**
428 * Tests whether numerical comparison matches.
429 *
430 * @test
431 */
432 public function globalVarConditionDoesNotMatchOnEmptyExpressionWithValueSetToZero()
433 {
434 $testKey = $this->getUniqueId('test');
435 $_GET = [];
436 $_POST = [$testKey => 0];
437 $this->assertFalse($this->matchCondition->match('[globalVar = GP:' . $testKey . '=]'));
438 $this->assertFalse($this->matchCondition->match('[globalVar = GP:' . $testKey . ' = ]'));
439 }
440
441 /**
442 * Tests whether string comparison matches.
443 *
444 * @test
445 */
446 public function globalStringConditionMatchesOnEqualExpression()
447 {
448 $this->assertTrue($this->matchCondition->match('[globalString = LIT:TYPO3.Test.Condition = TYPO3.Test.Condition]'));
449 $this->assertFalse($this->matchCondition->match('[globalString = LIT:TYPO3.Test.Condition = TYPO3]'));
450 }
451
452 /**
453 * Tests whether string comparison matches.
454 *
455 * @test
456 */
457 public function globalStringConditionMatchesOnEmptyExpressionWithValueSetToEmptyString()
458 {
459 $testKey = $this->getUniqueId('test');
460 $_GET = [];
461 $_POST = [$testKey => ''];
462 $this->assertTrue($this->matchCondition->match('[globalString = GP:' . $testKey . '=]'));
463 $this->assertTrue($this->matchCondition->match('[globalString = GP:' . $testKey . ' = ]'));
464 }
465
466 /**
467 * Tests whether string comparison matches.
468 *
469 * @test
470 */
471 public function globalStringConditionMatchesOnEmptyLiteralExpressionWithValueSetToEmptyString()
472 {
473 $this->assertTrue($this->matchCondition->match('[globalString = LIT:=]'));
474 $this->assertTrue($this->matchCondition->match('[globalString = LIT: = ]'));
475 }
476
477 /**
478 * Tests whether string comparison matches.
479 *
480 * @test
481 */
482 public function globalStringConditionMatchesWildcardExpression()
483 {
484 $this->assertTrue($this->matchCondition->match('[globalString = LIT:TYPO3.Test.Condition = TYPO3?Test?Condition]'));
485 $this->assertTrue($this->matchCondition->match('[globalString = LIT:TYPO3.Test.Condition = TYPO3.T*t.Condition]'));
486 $this->assertTrue($this->matchCondition->match('[globalString = LIT:TYPO3.Test.Condition = TYPO3?T*t?Condition]'));
487 // globalString is not implemented, because globalVar did the job
488 // Access with LIT is not possible in expression language, because constants available as variable
489 }
490
491 /**
492 * Tests whether string comparison matches.
493 *
494 * @test
495 */
496 public function globalStringConditionMatchesRegularExpression()
497 {
498 $this->assertTrue($this->matchCondition->match('[globalString = LIT:TYPO3.Test.Condition = /^[A-Za-z3.]+$/]'));
499 $this->assertTrue($this->matchCondition->match('[globalString = LIT:TYPO3.Test.Condition = /^TYPO3\\..+Condition$/]'));
500 $this->assertFalse($this->matchCondition->match('[globalString = LIT:TYPO3.Test.Condition = /^FALSE/]'));
501 }
502
503 /**
504 * Tests whether string comparison matches.
505 *
506 * @test
507 */
508 public function globalStringConditionMatchesEmptyRegularExpression()
509 {
510 $testKey = $this->getUniqueId('test');
511 $_SERVER[$testKey] = '';
512 $this->assertTrue($this->matchCondition->match('[globalString = _SERVER|' . $testKey . ' = /^$/]'));
513 }
514
515 /**
516 * Tests whether treeLevel comparison matches.
517 *
518 * @test
519 */
520 public function treeLevelConditionMatchesSingleValue()
521 {
522 $this->matchCondition->setRootline($this->rootline);
523 $this->assertTrue($this->matchCondition->match('[treeLevel = 2]'));
524 }
525
526 /**
527 * Tests whether treeLevel comparison matches.
528 *
529 * @test
530 */
531 public function treeLevelConditionMatchesMultipleValues()
532 {
533 $this->matchCondition->setRootline($this->rootline);
534 $this->assertTrue($this->matchCondition->match('[treeLevel = 999,998,2]'));
535 }
536
537 /**
538 * Tests whether treeLevel comparison matches.
539 *
540 * @test
541 */
542 public function treeLevelConditionDoesNotMatchFaultyValue()
543 {
544 $this->matchCondition->setRootline($this->rootline);
545 $this->assertFalse($this->matchCondition->match('[treeLevel = 999]'));
546 }
547
548 /**
549 * Tests whether treeLevel comparison matches when creating new pages.
550 *
551 * @test
552 */
553 public function treeLevelConditionMatchesCurrentPageIdWhileEditingNewPage()
554 {
555 $GLOBALS['SOBE'] = $this->createMock(\TYPO3\CMS\Backend\Controller\EditDocumentController::class);
556 $GLOBALS['SOBE']->elementsData = [
557 [
558 'table' => 'pages',
559 'uid' => 'NEW4adc6021e37e7',
560 'pid' => 121,
561 'cmd' => 'new',
562 'deleteAccess' => 0
563 ]
564 ];
565 $GLOBALS['SOBE']->data = [];
566 $this->matchCondition->setRootline($this->rootline);
567 $this->matchCondition->setPageId(121);
568 $this->assertTrue($this->matchCondition->match('[treeLevel = 3]'));
569 }
570
571 /**
572 * Tests whether treeLevel comparison matches when creating new pages.
573 *
574 * @test
575 */
576 public function treeLevelConditionMatchesCurrentPageIdWhileSavingNewPage()
577 {
578 $GLOBALS['SOBE'] = $this->createMock(\TYPO3\CMS\Backend\Controller\EditDocumentController::class);
579 $GLOBALS['SOBE']->elementsData = [
580 [
581 'table' => 'pages',
582 /// 999 is the uid of the page that was just created
583 'uid' => 999,
584 'pid' => 121,
585 'cmd' => 'edit',
586 'deleteAccess' => 1
587 ]
588 ];
589 $GLOBALS['SOBE']->data = [
590 'pages' => [
591 'NEW4adc6021e37e7' => [
592 'pid' => 121
593 ]
594 ]
595 ];
596 $this->matchCondition->setRootline($this->rootline);
597 $this->matchCondition->setPageId(121);
598 $this->assertTrue($this->matchCondition->match('[treeLevel = 3]'));
599 }
600
601 /**
602 * Tests whether a page Id is found in the previous rootline entries.
603 *
604 * @test
605 */
606 public function PIDupinRootlineConditionMatchesSinglePageIdInRootline()
607 {
608 $this->matchCondition->setRootline($this->rootline);
609 $this->matchCondition->setPageId(121);
610 $this->assertTrue($this->matchCondition->match('[PIDupinRootline = 111]'));
611 }
612
613 /**
614 * Tests whether a page Id is found in the previous rootline entries.
615 *
616 * @test
617 */
618 public function PIDupinRootlineConditionMatchesMultiplePageIdsInRootline()
619 {
620 $this->matchCondition->setRootline($this->rootline);
621 $this->matchCondition->setPageId(121);
622 $this->assertTrue($this->matchCondition->match('[PIDupinRootline = 999,111,101]'));
623 }
624
625 /**
626 * Tests whether a page Id is found in the previous rootline entries.
627 *
628 * @test
629 */
630 public function PIDupinRootlineConditionDoesNotMatchPageIdNotInRootline()
631 {
632 $this->matchCondition->setRootline($this->rootline);
633 $this->matchCondition->setPageId(121);
634 $this->assertFalse($this->matchCondition->match('[PIDupinRootline = 999]'));
635 }
636
637 /**
638 * Tests whether a page Id is found in the previous rootline entries.
639 *
640 * @test
641 */
642 public function PIDupinRootlineConditionDoesNotMatchLastPageIdInRootline()
643 {
644 $this->matchCondition->setRootline($this->rootline);
645 $this->matchCondition->setPageId(121);
646 $this->assertFalse($this->matchCondition->match('[PIDupinRootline = 121]'));
647 }
648
649 /**
650 * Tests whether a page Id is found in the previous rootline entries.
651 *
652 * @test
653 */
654 public function PIDupinRootlineConditionMatchesCurrentPageIdWhileEditingNewPage()
655 {
656 $GLOBALS['SOBE'] = $this->createMock(\TYPO3\CMS\Backend\Controller\EditDocumentController::class);
657 $GLOBALS['SOBE']->elementsData = [
658 [
659 'table' => 'pages',
660 'uid' => 'NEW4adc6021e37e7',
661 'pid' => 121,
662 'cmd' => 'new',
663 'deleteAccess' => 0
664 ]
665 ];
666 $GLOBALS['SOBE']->data = [];
667 $this->matchCondition->setRootline($this->rootline);
668 $this->matchCondition->setPageId(121);
669 $this->assertTrue($this->matchCondition->match('[PIDupinRootline = 121]'));
670 }
671
672 /**
673 * Tests whether a page Id is found in the previous rootline entries.
674 *
675 * @test
676 */
677 public function PIDupinRootlineConditionMatchesCurrentPageIdWhileSavingNewPage()
678 {
679 $GLOBALS['SOBE'] = $this->createMock(\TYPO3\CMS\Backend\Controller\EditDocumentController::class);
680 $GLOBALS['SOBE']->elementsData = [
681 [
682 'table' => 'pages',
683 /// 999 is the uid of the page that was just created
684 'uid' => 999,
685 'pid' => 121,
686 'cmd' => 'edit',
687 'deleteAccess' => 1
688 ]
689 ];
690 $GLOBALS['SOBE']->data = [
691 'pages' => [
692 'NEW4adc6021e37e7' => [
693 'pid' => 121
694 ]
695 ]
696 ];
697 $this->matchCondition->setRootline($this->rootline);
698 $this->matchCondition->setPageId(121);
699 $this->assertTrue($this->matchCondition->match('[PIDupinRootline = 121]'));
700 }
701
702 /**
703 * Tests whether a page Id is found in all rootline entries.
704 *
705 * @test
706 */
707 public function PIDinRootlineConditionMatchesSinglePageIdInRootline()
708 {
709 $this->matchCondition->setRootline($this->rootline);
710 $this->matchCondition->setPageId(121);
711 $this->assertTrue($this->matchCondition->match('[PIDinRootline = 111]'));
712 }
713
714 /**
715 * Tests whether a page Id is found in all rootline entries.
716 *
717 * @test
718 */
719 public function PIDinRootlineConditionMatchesMultiplePageIdsInRootline()
720 {
721 $this->matchCondition->setRootline($this->rootline);
722 $this->matchCondition->setPageId(121);
723 $this->assertTrue($this->matchCondition->match('[PIDinRootline = 999,111,101]'));
724 }
725
726 /**
727 * Tests whether a page Id is found in all rootline entries.
728 *
729 * @test
730 */
731 public function PIDinRootlineConditionMatchesLastPageIdInRootline()
732 {
733 $this->matchCondition->setRootline($this->rootline);
734 $this->matchCondition->setPageId(121);
735 $this->assertTrue($this->matchCondition->match('[PIDinRootline = 121]'));
736 }
737
738 /**
739 * Tests whether a page Id is found in all rootline entries.
740 *
741 * @test
742 */
743 public function PIDinRootlineConditionDoesNotMatchPageIdNotInRootline()
744 {
745 $this->matchCondition->setRootline($this->rootline);
746 $this->matchCondition->setPageId(121);
747 $this->assertFalse($this->matchCondition->match('[PIDinRootline = 999]'));
748 }
749
750 /**
751 * Tests whether the compatibility version can be evaluated.
752 * (e.g. 7.9 is compatible to 7.0 but not to 15.0)
753 *
754 * @test
755 */
756 public function compatVersionConditionMatchesOlderRelease()
757 {
758 $this->assertTrue($this->matchCondition->match('[compatVersion = 7.0]'));
759 }
760
761 /**
762 * Tests whether the compatibility version can be evaluated.
763 * (e.g. 7.9 is compatible to 7.0 but not to 15.0)
764 *
765 * @test
766 */
767 public function compatVersionConditionMatchesSameRelease()
768 {
769 $this->assertTrue($this->matchCondition->match('[compatVersion = ' . TYPO3_branch . ']'));
770 }
771
772 /**
773 * Tests whether the compatibility version can be evaluated.
774 * (e.g. 7.9 is compatible to 7.0 but not to 15.0)
775 *
776 * @test
777 */
778 public function compatVersionConditionDoesNotMatchNewerRelease()
779 {
780 $this->assertFalse($this->matchCondition->match('[compatVersion = 15.0]'));
781 }
782
783 /**
784 * Tests whether the generic fetching of variables works with the namespace 'GP'.
785 *
786 * @test
787 */
788 public function genericGetVariablesSucceedsWithNamespaceGP()
789 {
790 $_GET = ['testGet' => 'getTest'];
791 $_POST = ['testPost' => 'postTest'];
792 $this->assertTrue($this->matchCondition->match('[globalString = GP:testGet = getTest]'));
793 $this->assertTrue($this->matchCondition->match('[globalString = GP:testPost = postTest]'));
794 }
795
796 /**
797 * Tests whether the generic fetching of variables does not work with the namespace 'TSFE',
798 * since we are in the backend context here.
799 *
800 * @test
801 */
802 public function genericGetVariablesFailsWithNamespaceTSFE()
803 {
804 $GLOBALS['TSFE'] = new \stdClass();
805 $GLOBALS['TSFE']->id = 1234567;
806 $this->assertFalse($this->matchCondition->match('[globalString = TSFE:id = 1234567]'));
807 }
808
809 /**
810 * Tests whether the generic fetching of variables works with the namespace 'ENV'.
811 *
812 * @test
813 */
814 public function genericGetVariablesSucceedsWithNamespaceENV()
815 {
816 $testKey = $this->getUniqueId('test');
817 putenv($testKey . '=testValue');
818 $this->assertTrue($this->matchCondition->match('[globalString = ENV:' . $testKey . ' = testValue]'));
819 }
820
821 /**
822 * Tests whether the generic fetching of variables works with the namespace 'IENV'.
823 *
824 * @test
825 */
826 public function genericGetVariablesSucceedsWithNamespaceIENV()
827 {
828 $_SERVER['HTTP_HOST'] = GeneralUtility::getIndpEnv('TYPO3_HOST_ONLY') . ':1234567';
829 // getIndpEnv() is polluted after above call, clear cache to have it recalculate for subject execption
830 GeneralUtility::flushInternalRuntimeCaches();
831 $this->assertTrue($this->matchCondition->match('[globalString = IENV:TYPO3_PORT = 1234567]'));
832 }
833
834 /**
835 * Tests whether the generic fetching of variables works with any global namespace.
836 *
837 * @test
838 */
839 public function genericGetVariablesSucceedsWithAnyGlobalNamespace()
840 {
841 $GLOBALS[$this->testGlobalNamespace] = [
842 'first' => 'testFirst',
843 'second' => ['third' => 'testThird']
844 ];
845 $this->assertTrue($this->matchCondition->match('[globalString = ' . $this->testGlobalNamespace . '|first = testFirst]'));
846 $this->assertTrue($this->matchCondition->match('[globalString = ' . $this->testGlobalNamespace . '|second|third = testThird]'));
847 }
848
849 /**
850 * Tests whether determining a pageId works.
851 *
852 * @test
853 */
854 public function pageIdCanBeDeterminedWhileCallingModuleWithPageTree()
855 {
856 $_GET['id'] = 999;
857 $this->matchCondition->match('[globalVar = LIT:10 = 10]');
858 $this->assertEquals(999, $this->matchCondition->getPageId());
859 }
860
861 /**
862 * Tests whether determining a pageId works.
863 *
864 * @test
865 */
866 public function pageIdCanBeDeterminedWhileEditingAPageRecord()
867 {
868 $_GET['edit']['pages'][999] = 'edit';
869 $this->matchCondition->match('[globalVar = LIT:10 = 10]');
870 $this->assertEquals(999, $this->matchCondition->getPageId());
871 }
872
873 /**
874 * Tests whether determining a pageId works.
875 *
876 * @test
877 */
878 public function pageIdCanBeDeterminedWhileEditingARegularRecord()
879 {
880 $this->setUpDatabaseMockForDeterminePageId();
881 $_GET['edit'][$this->testTableName][13] = 'edit';
882 $this->matchCondition->match('[globalVar = LIT:10 = 10]');
883 $this->assertEquals(999, $this->matchCondition->getPageId());
884 }
885
886 /**
887 * Tests whether determining a pageId works.
888 *
889 * @test
890 */
891 public function pageIdCanBeDeterminedWhileCreatingARecord()
892 {
893 $_GET['edit']['pages'][999] = 'new';
894 $this->matchCondition->match('[globalVar = LIT:10 = 10]');
895 $this->assertEquals(999, $this->matchCondition->getPageId());
896 }
897
898 /**
899 * Tests whether determining a pageId works.
900 *
901 * @test
902 */
903 public function pageIdCanBeDeterminedWhileCreatingARecordAfterAnExistingRecord()
904 {
905 $this->setUpDatabaseMockForDeterminePageId();
906 $_GET['edit'][$this->testTableName][-13] = 'new';
907 $this->matchCondition->match('[globalVar = LIT:10 = 10]');
908 $this->assertEquals(999, $this->matchCondition->getPageId());
909 }
910
911 /**
912 * Tests whether determining a pageId works.
913 *
914 * @test
915 */
916 public function pageIdCanBeDeterminedWhileDeletingAPageRecord()
917 {
918 $_GET['cmd']['pages'][999]['delete'] = 1;
919 $this->matchCondition->match('[globalVar = LIT:10 = 10]');
920 $this->assertEquals(999, $this->matchCondition->getPageId());
921 }
922
923 /**
924 * Tests whether determining a pageId works.
925 *
926 * @test
927 */
928 public function pageIdCanBeDeterminedWhileCopyingARecordToAnotherPage()
929 {
930 $_GET['cmd']['pages'][121]['copy'] = 999;
931 $this->matchCondition->match('[globalVar = LIT:10 = 10]');
932 $this->assertEquals(999, $this->matchCondition->getPageId());
933 }
934
935 /**
936 * Tests whether determining a pageId works.
937 *
938 * @test
939 */
940 public function pageIdCanBeDeterminedWhileCopyingARecordAfterAnExistingRecord()
941 {
942 $this->setUpDatabaseMockForDeterminePageId();
943 $_GET['cmd'][$this->testTableName][121]['copy'] = -13;
944 $this->matchCondition->match('[globalVar = LIT:10 = 10]');
945 $this->assertEquals(999, $this->matchCondition->getPageId());
946 }
947
948 /**
949 * Tests whether determining a pageId works.
950 *
951 * @test
952 */
953 public function pageIdCanBeDeterminedWhileMovingARecordToAnotherPage()
954 {
955 $_GET['cmd']['pages'][121]['move'] = 999;
956 $this->matchCondition->match('[globalVar = LIT:10 = 10]');
957 $this->assertEquals(999, $this->matchCondition->getPageId());
958 }
959
960 /**
961 * @test
962 */
963 public function matchCallsTestConditionAndHandsOverParameters()
964 {
965 $this->expectException(TestConditionException::class);
966 $this->expectExceptionCode(1476109533);
967 $this->matchCondition->match('[TYPO3\\CMS\\Backend\\Tests\\UnitDeprecated\\Configuration\\TypoScript\\ConditionMatching\\Fixtures\\TestCondition = 7, != 6]');
968 }
969 }