From 5868effc963064593a3d483bb19dd5c1a2e2802f Mon Sep 17 00:00:00 2001 From: Sebastian Fischer Date: Sun, 1 Dec 2024 11:56:07 +0100 Subject: [PATCH 01/12] [TASK] Further reduce need to override partials and templates --- ...ontainerConfigurationIsAppliedListener.php | 8 +--- ...foreContainerPreviewIsRenderedListener.php | 16 +++++++ .../PageLayout/Grid/ColumnHeader.html | 44 +++++++++---------- Resources/Private/Templates/Grid.html | 15 ------- 4 files changed, 37 insertions(+), 46 deletions(-) delete mode 100644 Resources/Private/Templates/Grid.html diff --git a/Classes/EventListener/BeforeContainerConfigurationIsAppliedListener.php b/Classes/EventListener/BeforeContainerConfigurationIsAppliedListener.php index dc67c61..dfa6ee6 100644 --- a/Classes/EventListener/BeforeContainerConfigurationIsAppliedListener.php +++ b/Classes/EventListener/BeforeContainerConfigurationIsAppliedListener.php @@ -23,13 +23,7 @@ class BeforeContainerConfigurationIsAppliedListener #[AsEventListener('collapsible-container-beforecontainer', BeforeContainerConfigurationIsAppliedEvent::class)] public function __invoke(BeforeContainerConfigurationIsAppliedEvent $event): void { - $containerConfiguration = $event->getContainerConfiguration(); - - $containerConfiguration->setGridTemplate( - 'EXT:ew_collapsible_container/Resources/Private/Templates/Grid.html' - ); - - $containerConfiguration->setGridPartialPaths([ + $event->getContainerConfiguration()->setGridPartialPaths([ 'EXT:backend/Resources/Private/Partials/', 'EXT:container/Resources/Private/Partials/', 'EXT:ew_collapsible_container/Resources/Private/Partials/', diff --git a/Classes/EventListener/BeforeContainerPreviewIsRenderedListener.php b/Classes/EventListener/BeforeContainerPreviewIsRenderedListener.php index a255886..dff3f5d 100644 --- a/Classes/EventListener/BeforeContainerPreviewIsRenderedListener.php +++ b/Classes/EventListener/BeforeContainerPreviewIsRenderedListener.php @@ -21,9 +21,15 @@ use Evoweb\EwCollapsibleContainer\Xclass\ContainerGridColumn; use TYPO3\CMS\Core\Attribute\AsEventListener; use TYPO3\CMS\Core\Authentication\BackendUserAuthentication; +use TYPO3\CMS\Core\Page\JavaScriptModuleInstruction; +use TYPO3\CMS\Core\Page\PageRenderer; class BeforeContainerPreviewIsRenderedListener { + public function __construct(protected PageRenderer $pageRenderer) + { + } + #[AsEventListener('collapsible-container-beforepreview', BeforeContainerPreviewIsRenderedEvent::class)] public function __invoke(BeforeContainerPreviewIsRenderedEvent $event): void { @@ -38,6 +44,8 @@ public function __invoke(BeforeContainerPreviewIsRenderedEvent $event): void 'showMinItemsWarning' => $this->getShowMinItemsWarning($column, $countOfHiddenItems) ]); } + + $this->addFrontendResources(); } protected function getCountOfHiddenItems(ContainerGridColumn $columnObject): int @@ -71,6 +79,14 @@ protected function getShowMinItemsWarning(ContainerGridColumn $columnObject, int return $itemCount > 0 && ($itemCount - $hiddenItemCount) < $minItems; } + protected function addFrontendResources(): void + { + $this->pageRenderer->addCssFile('EXT:ew_collapsible_container/Resources/Public/Css/container.css'); + $this->pageRenderer->getJavaScriptRenderer()->addJavaScriptModuleInstruction( + JavaScriptModuleInstruction::create('@evoweb/ew-collapsible-container/container.js') + ); + } + protected function getBackendUser(): BackendUserAuthentication { return $GLOBALS['BE_USER']; diff --git a/Resources/Private/Partials/PageLayout/Grid/ColumnHeader.html b/Resources/Private/Partials/PageLayout/Grid/ColumnHeader.html index 4e167b1..f353971 100644 --- a/Resources/Private/Partials/PageLayout/Grid/ColumnHeader.html +++ b/Resources/Private/Partials/PageLayout/Grid/ColumnHeader.html @@ -39,22 +39,20 @@ - - - - - - - - + + + + + + @@ -73,14 +71,12 @@ - -
- - {f:translate(key: 'LLL:EXT:ew_collapsible_container/Resources/Private/Language/locallang.xlf:contentcollapsed')} -
-
+
+ + {f:translate(key: 'LLL:EXT:ew_collapsible_container/Resources/Private/Language/locallang.xlf:contentcollapsed')} +
diff --git a/Resources/Private/Templates/Grid.html b/Resources/Private/Templates/Grid.html deleted file mode 100644 index a6adcca..0000000 --- a/Resources/Private/Templates/Grid.html +++ /dev/null @@ -1,15 +0,0 @@ - - - - - - - - - - From 2a67c37efe53a4e0cd52c09d8f0f9605d6dc0913 Mon Sep 17 00:00:00 2001 From: Sebastian Fischer Date: Sun, 1 Dec 2024 11:58:16 +0100 Subject: [PATCH 02/12] [CHORE] Replace custom documentReady check with DocumentService --- Resources/Public/JavaScript/container.js | 16 ++++++++-------- 1 file changed, 8 insertions(+), 8 deletions(-) diff --git a/Resources/Public/JavaScript/container.js b/Resources/Public/JavaScript/container.js index 6b625b6..cdf1a35 100644 --- a/Resources/Public/JavaScript/container.js +++ b/Resources/Public/JavaScript/container.js @@ -9,6 +9,7 @@ * LICENSE.txt file that was distributed with this source code. */ +import DocumentService from '@typo3/core/document-service.js'; import PersistentStorage from '@typo3/backend/storage/persistent.js'; class ContainerToggle { @@ -16,22 +17,21 @@ class ContainerToggle { columnExpand = '.t3js-expand-column'; + /** + * @type {PersistentStorage} + */ persistentStorage = null; storageKey = 'moduleData.list.containerExpanded'; constructor() { this.persistentStorage = PersistentStorage; - if (document.readyState === 'loading') { - document.addEventListener('DOMContentLoaded', () => { - this.initialized(); - }); - } else { - this.initialized(); - } + DocumentService.ready().then(() => { + this.initialize(); + }); } - initialized() { + initialize() { this.initializeContainerToggle(); this.initializeExpandColumn(); } From bc60b885864cdd644242c67da857839b5e564a41 Mon Sep 17 00:00:00 2001 From: Sebastian Fischer Date: Sun, 1 Dec 2024 12:53:10 +0100 Subject: [PATCH 03/12] [CHORE] Add folder to gitignore --- .gitattributes | 3 +++ 1 file changed, 3 insertions(+) diff --git a/.gitattributes b/.gitattributes index 3a01b37..c1108e7 100644 --- a/.gitattributes +++ b/.gitattributes @@ -1,2 +1,5 @@ +/.github/ export-ignore +/Build/ export-ignore +/Tests/ export-ignore /.gitattributes export-ignore /.gitignore export-ignore From af4756ff1b49ab0d1ecb34c91ceb4d5a35a86750 Mon Sep 17 00:00:00 2001 From: Sebastian Fischer Date: Sun, 1 Dec 2024 13:11:51 +0100 Subject: [PATCH 04/12] [TASK] Refactor settings partials in container configuration --- ...ontainerConfigurationIsAppliedListener.php | 8 ++-- ...inerConfigurationIsAppliedListenerTest.php | 45 +++++++++++++++++++ 2 files changed, 48 insertions(+), 5 deletions(-) create mode 100644 Tests/Functional/EventListener/BeforeContainerConfigurationIsAppliedListenerTest.php diff --git a/Classes/EventListener/BeforeContainerConfigurationIsAppliedListener.php b/Classes/EventListener/BeforeContainerConfigurationIsAppliedListener.php index dfa6ee6..5cc04e8 100644 --- a/Classes/EventListener/BeforeContainerConfigurationIsAppliedListener.php +++ b/Classes/EventListener/BeforeContainerConfigurationIsAppliedListener.php @@ -23,10 +23,8 @@ class BeforeContainerConfigurationIsAppliedListener #[AsEventListener('collapsible-container-beforecontainer', BeforeContainerConfigurationIsAppliedEvent::class)] public function __invoke(BeforeContainerConfigurationIsAppliedEvent $event): void { - $event->getContainerConfiguration()->setGridPartialPaths([ - 'EXT:backend/Resources/Private/Partials/', - 'EXT:container/Resources/Private/Partials/', - 'EXT:ew_collapsible_container/Resources/Private/Partials/', - ]); + $event->getContainerConfiguration()->addGridPartialPath( + 'EXT:ew_collapsible_container/Resources/Private/Partials/' + ); } } diff --git a/Tests/Functional/EventListener/BeforeContainerConfigurationIsAppliedListenerTest.php b/Tests/Functional/EventListener/BeforeContainerConfigurationIsAppliedListenerTest.php new file mode 100644 index 0000000..bafa4cb --- /dev/null +++ b/Tests/Functional/EventListener/BeforeContainerConfigurationIsAppliedListenerTest.php @@ -0,0 +1,45 @@ +__invoke($event); + + $this->assertContains( + 'EXT:ew_collapsible_container/Resources/Private/Partials/', + $event->getContainerConfiguration()->getGridPartialPaths() + ); + } +} From f12ccd3aed7d5f68e8b12893149041713e0f16d2 Mon Sep 17 00:00:00 2001 From: Sebastian Fischer Date: Sun, 1 Dec 2024 17:45:07 +0100 Subject: [PATCH 05/12] [TASK] Add test for ContainerGridColumn --- .../Xclass/ContainerGridColumnTest.php | 66 +++++++++++++++++++ 1 file changed, 66 insertions(+) create mode 100644 Tests/Functional/Xclass/ContainerGridColumnTest.php diff --git a/Tests/Functional/Xclass/ContainerGridColumnTest.php b/Tests/Functional/Xclass/ContainerGridColumnTest.php new file mode 100644 index 0000000..3eeec62 --- /dev/null +++ b/Tests/Functional/Xclass/ContainerGridColumnTest.php @@ -0,0 +1,66 @@ +importCSVDataSet(__DIR__ . '/../../Fixtures/be_users.csv'); + $backendUser = $this->setUpBackendUser(1); + $GLOBALS['LANG'] = $this->get(LanguageServiceFactory::class)->createFromUserPreferences($backendUser); + + $pageLayoutContext = new PageLayoutContext( + [], + new BackendLayout('', '', []), + new Site('test', 1, []), + new DrawingConfiguration(), + $this->get(ServerRequestFactory::class)->createServerRequest('GET', '/'), + ); + + $container = new Container([], [], 0); + + $subject = new ContainerGridColumn( + $pageLayoutContext, + [ + 'colPos' => 200, + ], + $container, + '', + false + ); + + $subject->setOverride([ + 'countOfHiddenItems' => 0, + 'collapsed' => false, + 'showMinItemsWarning' => false, + ]); + + $this->assertArrayHasKey('countOfHiddenItems', $subject->getDefinition()); + } +} From 25fa36b6c8768fe5331e710a902f78ea3c1c80f1 Mon Sep 17 00:00:00 2001 From: Sebastian Fischer Date: Sun, 1 Dec 2024 21:05:58 +0100 Subject: [PATCH 06/12] [CHORE] Remove creating symlink --- composer.json | 6 ------ 1 file changed, 6 deletions(-) diff --git a/composer.json b/composer.json index f866afd..62d850f 100644 --- a/composer.json +++ b/composer.json @@ -50,12 +50,6 @@ "rm .gitignore", "sed -i \"s/version' => '.*'/version' => '$(echo ${GITHUB_REF} | cut -d / -f 3)'/\" ext_emconf.php\n" ], - "post-install-cmd": [ - "ln -sf vendor/typo3/testing-framework/Resources/Core/Build/ Build/phpunit;" - ], - "post-update-cmd": [ - "@post-install-cmd" - ], "post-autoload-dump": [ "TYPO3\\TestingFramework\\Composer\\ExtensionTestEnvironment::prepare" ] From 7c4d2d35e65e8f0348700009faf5d22864ee04ca Mon Sep 17 00:00:00 2001 From: Sebastian Fischer Date: Sun, 1 Dec 2024 22:22:11 +0100 Subject: [PATCH 07/12] [CHORE] Add autoload info --- composer.json | 5 +++++ 1 file changed, 5 insertions(+) diff --git a/composer.json b/composer.json index 62d850f..441c00b 100644 --- a/composer.json +++ b/composer.json @@ -58,5 +58,10 @@ "psr-4": { "Evoweb\\EwCollapsibleContainer\\": "Classes/" } + }, + "autoload-dev": { + "psr-4": { + "Evoweb\\EwCollapsibleContainer\\Tests\\": "Tests/" + } } } From d2ff4f1322959c4a95be4c049ccf0f55256a1f22 Mon Sep 17 00:00:00 2001 From: Sebastian Fischer Date: Sun, 1 Dec 2024 22:22:53 +0100 Subject: [PATCH 08/12] [TASK] Improve event generation --- Build/phpunit/FunctionalTests.xml | 46 ++++ Build/phpunit/FunctionalTestsBootstrap.php | 31 +++ Tests/Fixtures/be_users.csv | 6 + Tests/Fixtures/tt_content.csv | 9 + ...ContainerPreviewIsRenderedListenerTest.php | 206 ++++++++++++++++++ 5 files changed, 298 insertions(+) create mode 100644 Build/phpunit/FunctionalTests.xml create mode 100644 Build/phpunit/FunctionalTestsBootstrap.php create mode 100644 Tests/Fixtures/be_users.csv create mode 100644 Tests/Fixtures/tt_content.csv create mode 100644 Tests/Functional/EventListener/BeforeContainerPreviewIsRenderedListenerTest.php diff --git a/Build/phpunit/FunctionalTests.xml b/Build/phpunit/FunctionalTests.xml new file mode 100644 index 0000000..0afe47f --- /dev/null +++ b/Build/phpunit/FunctionalTests.xml @@ -0,0 +1,46 @@ + + + + + + + ../../../../../../typo3/sysext/*/Tests/Functional/ + + + + + + + diff --git a/Build/phpunit/FunctionalTestsBootstrap.php b/Build/phpunit/FunctionalTestsBootstrap.php new file mode 100644 index 0000000..9882f8f --- /dev/null +++ b/Build/phpunit/FunctionalTestsBootstrap.php @@ -0,0 +1,31 @@ +defineOriginalRootPath(); + $testbase->createDirectory(ORIGINAL_ROOT . 'typo3temp/var/tests'); + $testbase->createDirectory(ORIGINAL_ROOT . 'typo3temp/var/transient'); +})(); diff --git a/Tests/Fixtures/be_users.csv b/Tests/Fixtures/be_users.csv new file mode 100644 index 0000000..2603e55 --- /dev/null +++ b/Tests/Fixtures/be_users.csv @@ -0,0 +1,6 @@ +be_users,,,,,,,,,,,,,,,,, +,uid,pid,tstamp,username,password,admin,disable,starttime,endtime,options,crdate,workspace_perms,deleted,TSconfig,lastlogin,workspace_id,usergroup, +,1,0,1366642540,admin,$1$tCrlLajZ$C0sikFQQ3SWaFAZ1Me0Z/1,1,0,0,0,0,1366642540,1,0,,1371033743,0,, +,2,0,1366642540,editor_no_group,$1$tCrlLajZ$C0sikFQQ3SWaFAZ1Me0Z/1,0,0,0,0,3,1366642540,1,0,,1371033743,0,, +,3,0,1366642540,editor_with_both_groups,$1$tCrlLajZ$C0sikFQQ3SWaFAZ1Me0Z/1,0,0,0,0,3,1366642540,1,0,,1371033743,0,"1,2", +,4,0,1366642540,editor_with_one_group,$1$tCrlLajZ$C0sikFQQ3SWaFAZ1Me0Z/1,0,0,0,0,3,1366642540,1,0,,1371033743,0,"2", diff --git a/Tests/Fixtures/tt_content.csv b/Tests/Fixtures/tt_content.csv new file mode 100644 index 0000000..587a7ab --- /dev/null +++ b/Tests/Fixtures/tt_content.csv @@ -0,0 +1,9 @@ +pages,,,, +,uid,pid,title,slug, +,1,0,Startpage,/startpage, +tt_content,,,,,, +,uid,pid,header,CType,colPos,tx_container_parent,hidden, +,1,1,Test Container,test-container,0,0,0, +,2,1,Test Child 1,test-child,200,1,0, +,3,1,Test Child 2,test-child,200,1,0, +,4,1,Test Child 3,test-child,200,1,1, diff --git a/Tests/Functional/EventListener/BeforeContainerPreviewIsRenderedListenerTest.php b/Tests/Functional/EventListener/BeforeContainerPreviewIsRenderedListenerTest.php new file mode 100644 index 0000000..a531732 --- /dev/null +++ b/Tests/Functional/EventListener/BeforeContainerPreviewIsRenderedListenerTest.php @@ -0,0 +1,206 @@ +configureTCA(); + + $this->importCSVDataSet(__DIR__ . '/../../Fixtures/tt_content.csv'); + $this->importCSVDataSet(__DIR__ . '/../../Fixtures/be_users.csv'); + $backendUser = $this->setUpBackendUser(1); + $GLOBALS['LANG'] = $this->get(LanguageServiceFactory::class)->createFromUserPreferences($backendUser); + } + + protected function configureTCA(): void + { + $configuration = new ContainerConfiguration( + 'test-container', + 'CType.I.test-container', + 'CType.I.test-container-plus_wiz_description', + [ + [ + [ + 'name' => 'Elements', + 'colPos' => 200, + 'allowed' => [ + 'CType' => 'test-child', + ], + 'collapsed' => true, + ] + ] + ] + ); + + $configuration->setGroup('ew_fischer'); + $configuration->setIcon('content-card-group'); + + $this->get(Registry::class)->configureContainer($configuration); + + $GLOBALS['TCA']['tt_content']['ctrl']['typeicon_classes']['test-container'] = 'content-card-group'; + } + + protected function getContentRecords(string $field, int $uid): array + { + /** @var QueryBuilder $queryBuilder */ + $queryBuilder = $this->get(ConnectionPool::class)->getQueryBuilderForTable('tt_content'); + $queryBuilder->getRestrictions()->removeAll(); + return $queryBuilder + ->select('*') + ->from('tt_content') + ->where($queryBuilder->expr()->eq($field, $uid)) + ->executeQuery() + ->fetchAssociative(); + } + + protected function getBeforeContainerPreviewIsRenderedEvent(array $record): ?BeforeContainerPreviewIsRenderedEvent + { + $context = new PageLayoutContext( + [], + new BackendLayout('', '', []), + new Site('test', 1, []), + new DrawingConfiguration(), + $this->get(ServerRequestFactory::class)->createServerRequest('GET', '/'), + ); + $item = new GridColumnItem($context, (new GridColumn($context, [])), $record); + $grid = new Grid($context); + + try { + $containerFactory = $this->get(ContainerFactory::class); + $container = $containerFactory->buildContainer((int)$record['uid']); + } catch (Exception $e) { + // not a container + return null; + } + + /** @var Registry $tcaRegistry */ + $tcaRegistry = $this->get(Registry::class); + $containerGrid = $tcaRegistry->getGrid($record['CType']); + foreach ($containerGrid as $cols) { + $rowObject = GeneralUtility::makeInstance(GridRow::class, $context); + foreach ($cols as $col) { + $columnObject = GeneralUtility::makeInstance( + ContainerGridColumn::class, + $context, + $col, + $container, + '', + false + ); + $rowObject->addColumn($columnObject); + if (isset($col['colPos'])) { + $records = $container->getChildrenByColPos($col['colPos']); + foreach ($records as $contentRecord) { + $columnItem = GeneralUtility::makeInstance( + ContainerGridColumnItem::class, + $context, + $columnObject, + $contentRecord, + $container, + '' + ); + $columnObject->addItem($columnItem); + } + } + } + $grid->addRow($rowObject); + } + + /** @var StandaloneView $view */ + $view = $this->get(StandaloneView::class); + + return new BeforeContainerPreviewIsRenderedEvent($container, $view, $grid, $item); + } + + #[Test] + public function getCountOfHiddenItems(): void + { + $containerRecord = $this->getContentRecords('tx_container_parent', 0); + $event = $this->getBeforeContainerPreviewIsRenderedEvent($containerRecord); + + /** @var PageRenderer $pageRenderer */ + $pageRenderer = $this->get(PageRenderer::class); + + $subject = new BeforeContainerPreviewIsRenderedListener($pageRenderer); + $subject->__invoke($event); + + $columns = $event->getGrid()->getColumns(); + } + + #[Test] + public function addFrontendResourcesAddJavascriptAndStylesheets(): void + { + $containerRecord = $this->getContentRecords('tx_container_parent', 0); + $event = $this->getBeforeContainerPreviewIsRenderedEvent($containerRecord); + + /** @var PageRenderer $pageRenderer */ + $pageRenderer = $this->get(PageRenderer::class); + + $subject = new BeforeContainerPreviewIsRenderedListener($pageRenderer); + $subject->__invoke($event); + + $reflectedClass = new \ReflectionClass($pageRenderer); + $property = $reflectedClass->getProperty('cssFiles'); + + $this->assertArrayHasKey( + 'EXT:ew_collapsible_container/Resources/Public/Css/container.css', + $property->getValue($pageRenderer) + ); + + $moduleName = '@evoweb/ew-collapsible-container/container.js'; + $javascriptInstruction = array_map( + fn (array $item) => $item['payload']->getName() === $moduleName ? $moduleName : '', + $pageRenderer->getJavaScriptRenderer()->toArray() + ); + + $this->assertContains($moduleName, $javascriptInstruction); + } +} From 11197d0a8de6e13e115112f7dcc7d08ec317d3c5 Mon Sep 17 00:00:00 2001 From: Sebastian Fischer Date: Mon, 2 Dec 2024 07:37:18 +0100 Subject: [PATCH 09/12] [CHORE] Remove phpunit from cleanup --- Build/Scripts/additionalTests.sh | 1 - 1 file changed, 1 deletion(-) diff --git a/Build/Scripts/additionalTests.sh b/Build/Scripts/additionalTests.sh index 86b29a3..c809c7d 100755 --- a/Build/Scripts/additionalTests.sh +++ b/Build/Scripts/additionalTests.sh @@ -430,7 +430,6 @@ additionalCleanTestFiles() { rm -rf \ .cache \ bin/ \ - Build/phpunit \ Build/vendor/ \ Build/Web/ \ Documentation-GENERATED-temp/ \ From a0776c86ccd4977b97eb5fe115b45a72adbcf6d4 Mon Sep 17 00:00:00 2001 From: Sebastian Fischer Date: Wed, 4 Dec 2024 18:58:55 +0100 Subject: [PATCH 10/12] [TASK] Remove deprecated code usage in functional tests --- ...ContainerPreviewIsRenderedListenerTest.php | 82 +++++++++++++++---- 1 file changed, 67 insertions(+), 15 deletions(-) diff --git a/Tests/Functional/EventListener/BeforeContainerPreviewIsRenderedListenerTest.php b/Tests/Functional/EventListener/BeforeContainerPreviewIsRenderedListenerTest.php index a531732..1d88c09 100644 --- a/Tests/Functional/EventListener/BeforeContainerPreviewIsRenderedListenerTest.php +++ b/Tests/Functional/EventListener/BeforeContainerPreviewIsRenderedListenerTest.php @@ -17,12 +17,15 @@ use B13\Container\Backend\Grid\ContainerGridColumn; use B13\Container\Backend\Grid\ContainerGridColumnItem; +use B13\Container\Domain\Factory\Database; use B13\Container\Domain\Factory\Exception; use B13\Container\Domain\Factory\PageView\Backend\ContainerFactory; +use B13\Container\Domain\Model\Container; use B13\Container\Events\BeforeContainerPreviewIsRenderedEvent; use B13\Container\Tca\ContainerConfiguration; use B13\Container\Tca\Registry; use Evoweb\EwCollapsibleContainer\EventListener\BeforeContainerPreviewIsRenderedListener; +use PHPUnit\Framework\Attributes\DataProvider; use PHPUnit\Framework\Attributes\Test; use TYPO3\CMS\Backend\View\BackendLayout\BackendLayout; use TYPO3\CMS\Backend\View\BackendLayout\Grid\Grid; @@ -74,7 +77,6 @@ protected function configureTCA(): void 'allowed' => [ 'CType' => 'test-child', ], - 'collapsed' => true, ] ] ] @@ -113,17 +115,21 @@ protected function getBeforeContainerPreviewIsRenderedEvent(array $record): ?Bef $item = new GridColumnItem($context, (new GridColumn($context, [])), $record); $grid = new Grid($context); - try { - $containerFactory = $this->get(ContainerFactory::class); - $container = $containerFactory->buildContainer((int)$record['uid']); - } catch (Exception $e) { - // not a container - return null; + $language = (int)$record['sys_language_uid']; + /** @var Database $database */ + $database = $this->get(Database::class); + $children = $database->fetchRecordsByParentAndLanguage((int)$record['uid'], $language); + $childRecordByColPosKey = []; + foreach ($children as $child) { + if (empty($childRecordByColPosKey[$child['colPos']])) { + $childRecordByColPosKey[$child['colPos']] = []; + } + $childRecordByColPosKey[$child['colPos']][] = $child; } - /** @var Registry $tcaRegistry */ - $tcaRegistry = $this->get(Registry::class); - $containerGrid = $tcaRegistry->getGrid($record['CType']); + $container = GeneralUtility::makeInstance(Container::class, $record, $childRecordByColPosKey, $language); + + $containerGrid = $this->get(Registry::class)->getGrid($record['CType']); foreach ($containerGrid as $cols) { $rowObject = GeneralUtility::makeInstance(GridRow::class, $context); foreach ($cols as $col) { @@ -155,7 +161,9 @@ protected function getBeforeContainerPreviewIsRenderedEvent(array $record): ?Bef } /** @var StandaloneView $view */ - $view = $this->get(StandaloneView::class); + $view = $this->getMockBuilder(StandaloneView::class) + ->disableOriginalConstructor() + ->getMock(); return new BeforeContainerPreviewIsRenderedEvent($container, $view, $grid, $item); } @@ -166,13 +174,57 @@ public function getCountOfHiddenItems(): void $containerRecord = $this->getContentRecords('tx_container_parent', 0); $event = $this->getBeforeContainerPreviewIsRenderedEvent($containerRecord); - /** @var PageRenderer $pageRenderer */ - $pageRenderer = $this->get(PageRenderer::class); + $subject = new BeforeContainerPreviewIsRenderedListener($this->get(PageRenderer::class)); + $subject->__invoke($event); - $subject = new BeforeContainerPreviewIsRenderedListener($pageRenderer); + $definition = $event->getGrid()->getColumns()[200]->getDefinition(); + $this->assertEquals(1, $definition['countOfHiddenItems']); + } + + public static function getCollapsedProvider(): array + { + return [ + 'falseIsDefault' => [ false ], + 'trueIsDefault' => [ true ], + ]; + } + + #[Test] + #[DataProvider('getCollapsedProvider')] + public function getCollapsed(bool $state): void + { + $GLOBALS['TCA']['tt_content']['containerConfiguration']['test-container']['grid'][0][0]['collapsed'] = $state; + $containerRecord = $this->getContentRecords('tx_container_parent', 0); + $event = $this->getBeforeContainerPreviewIsRenderedEvent($containerRecord); + + $subject = new BeforeContainerPreviewIsRenderedListener($this->get(PageRenderer::class)); + $subject->__invoke($event); + + $definition = $event->getGrid()->getColumns()[200]->getDefinition(); + $this->assertEquals($state, $definition['collapsed']); + } + + public static function showMinItemsProvider(): array + { + return [ + 'minItemsIsHigherThenAvailableItems' => [3, true], + 'minItemsIsNotHigherThenAvailableItems' => [2, false], + ]; + } + + #[Test] + #[DataProvider('showMinItemsProvider')] + public function getShowMinItemsWarning(int $minitems, bool $expected): void + { + $GLOBALS['TCA']['tt_content']['containerConfiguration']['test-container']['grid'][0][0]['minitems'] = $minitems; + $containerRecord = $this->getContentRecords('tx_container_parent', 0); + $event = $this->getBeforeContainerPreviewIsRenderedEvent($containerRecord); + + $subject = new BeforeContainerPreviewIsRenderedListener($this->get(PageRenderer::class)); $subject->__invoke($event); - $columns = $event->getGrid()->getColumns(); + $definition = $event->getGrid()->getColumns()[200]->getDefinition(); + $this->assertEquals($expected, $definition['showMinItemsWarning']); } #[Test] From 4f9d02d8f6e32653d53bca572842b0d99c37dec4 Mon Sep 17 00:00:00 2001 From: Sebastian Fischer Date: Wed, 4 Dec 2024 20:37:30 +0100 Subject: [PATCH 11/12] [TASK] Activate functional tests --- .github/workflows/ci.yml | 14 +++++++------- Build/Scripts/test.sh | 10 +++++----- 2 files changed, 12 insertions(+), 12 deletions(-) diff --git a/.github/workflows/ci.yml b/.github/workflows/ci.yml index 1c0b0ea..a870292 100644 --- a/.github/workflows/ci.yml +++ b/.github/workflows/ci.yml @@ -97,13 +97,13 @@ jobs: -p ${{ matrix.packages.php }} \ -s composerValidate -# - name: Functional tests with sqlite -# run: | -# Build/Scripts/runTests.sh \ -# -p ${{ matrix.packages.php }} \ -# -d sqlite \ -# -s functional ${{ matrix.packages.testpath }} -# + - name: Functional tests with sqlite + run: | + Build/Scripts/runTests.sh \ + -p ${{ matrix.packages.php }} \ + -d sqlite \ + -s functional ${{ matrix.packages.testpath }} + # - name: Unit tests with sqlite # run: | # Build/Scripts/runTests.sh \ diff --git a/Build/Scripts/test.sh b/Build/Scripts/test.sh index b6d332a..0fc66e7 100755 --- a/Build/Scripts/test.sh +++ b/Build/Scripts/test.sh @@ -102,11 +102,11 @@ runFunctionalTests () { -s composerValidate || exit 1 ; \ EXIT_CODE_VALIDATE=$? -# ./runTests.sh \ -# -p ${PHP_VERSION} \ -# -d sqlite \ -# -s functional ${TEST_PATH} || exit 1 ; \ -# EXIT_CODE_FUNCTIONAL=$? + ./runTests.sh \ + -p ${PHP_VERSION} \ + -d sqlite \ + -s functional ${TEST_PATH} || exit 1 ; \ + EXIT_CODE_FUNCTIONAL=$? echo "###########################################################################" >&2 echo " Finished unit and/or functional tests with" >&2 From ffbd04d07e51fb1945fc05832630f3cf49f274fb Mon Sep 17 00:00:00 2001 From: Sebastian Fischer Date: Wed, 4 Dec 2024 21:31:38 +0100 Subject: [PATCH 12/12] [CHORE] Raise version number --- Documentation/guides.xml | 4 ++-- ext_emconf.php | 2 +- 2 files changed, 3 insertions(+), 3 deletions(-) diff --git a/Documentation/guides.xml b/Documentation/guides.xml index 8cc20c8..4268397 100644 --- a/Documentation/guides.xml +++ b/Documentation/guides.xml @@ -16,8 +16,8 @@ interlink-shortcode="evoweb/sf-books" /> diff --git a/ext_emconf.php b/ext_emconf.php index da3faea..453ba56 100644 --- a/ext_emconf.php +++ b/ext_emconf.php @@ -8,7 +8,7 @@ 'author_email' => 'ew-collapsible-container@evoweb.de', 'author_company' => 'evoWeb', 'state' => 'stable', - 'version' => '2.1.0', + 'version' => '2.2.0', 'constraints' => [ 'depends' => [ 'typo3' => '13.4.0-13.4.99',