diff --git a/app/code/Magento/Theme/Controller/Adminhtml/System/Design/Theme/Index.php b/app/code/Magento/Theme/Controller/Adminhtml/System/Design/Theme/Index.php index 4bae57f80209e..d51fd658075f1 100644 --- a/app/code/Magento/Theme/Controller/Adminhtml/System/Design/Theme/Index.php +++ b/app/code/Magento/Theme/Controller/Adminhtml/System/Design/Theme/Index.php @@ -21,6 +21,7 @@ public function execute() { $this->_view->loadLayout(); $this->_setActiveMenu('Magento_Theme::system_design_theme'); + $this->_view->getLayout()->getBlock('page.title')->setPageTitle('Themes'); $this->_view->renderLayout(); } } diff --git a/app/code/Magento/Theme/Model/ResourceModel/Theme/Collection.php b/app/code/Magento/Theme/Model/ResourceModel/Theme/Collection.php index f2f95d24a368b..f9dd501520109 100644 --- a/app/code/Magento/Theme/Model/ResourceModel/Theme/Collection.php +++ b/app/code/Magento/Theme/Model/ResourceModel/Theme/Collection.php @@ -17,6 +17,11 @@ class Collection extends \Magento\Framework\Model\ResourceModel\Db\Collection\Ab */ const DEFAULT_PAGE_SIZE = 6; + /** + * @var string + */ + protected $_idFieldName = 'theme_id'; + /** * Collection initialization * diff --git a/app/code/Magento/Theme/Model/ResourceModel/Theme/Grid/Collection.php b/app/code/Magento/Theme/Model/ResourceModel/Theme/Grid/Collection.php index f708b3c7889f3..c4a7bb11a78f7 100644 --- a/app/code/Magento/Theme/Model/ResourceModel/Theme/Grid/Collection.php +++ b/app/code/Magento/Theme/Model/ResourceModel/Theme/Grid/Collection.php @@ -7,13 +7,15 @@ /** * Theme grid collection + * @deprecated + * @see \Magento\Theme\Ui\Component\Theme\DataProvider\SearchResult */ class Collection extends \Magento\Theme\Model\ResourceModel\Theme\Collection { /** * Add area filter * - * @return \Magento\Theme\Model\ResourceModel\Theme\Collection + * @return $this */ protected function _initSelect() { diff --git a/app/code/Magento/Theme/Test/Unit/Controller/Adminhtml/System/Design/Theme/IndexTest.php b/app/code/Magento/Theme/Test/Unit/Controller/Adminhtml/System/Design/Theme/IndexTest.php index a5acb67f93974..213d8dde8689f 100644 --- a/app/code/Magento/Theme/Test/Unit/Controller/Adminhtml/System/Design/Theme/IndexTest.php +++ b/app/code/Magento/Theme/Test/Unit/Controller/Adminhtml/System/Design/Theme/IndexTest.php @@ -28,13 +28,18 @@ public function testIndexAction() ->method('getMenuModel') ->will($this->returnValue($menuModel)); + $titleBlock = $this->createMock(\Magento\Theme\Block\Html\Title::class); + $titleBlock->expects($this->once())->method('setPageTitle'); + $layout = $this->createMock(\Magento\Framework\View\LayoutInterface::class); $layout->expects($this->any()) ->method('getBlock') - ->with($this->equalTo('menu')) - ->will($this->returnValue($menuBlock)); + ->willReturnMap([ + ['menu', $menuBlock], + ['page.title', $titleBlock] + ]); - $this->view->expects($this->once()) + $this->view->expects($this->any()) ->method('getLayout') ->will($this->returnValue($layout)); diff --git a/app/code/Magento/Theme/Test/Unit/Ui/Component/Listing/Column/ViewActionTest.php b/app/code/Magento/Theme/Test/Unit/Ui/Component/Listing/Column/ViewActionTest.php new file mode 100644 index 0000000000000..03d1fe70f2f07 --- /dev/null +++ b/app/code/Magento/Theme/Test/Unit/Ui/Component/Listing/Column/ViewActionTest.php @@ -0,0 +1,121 @@ +objectManager = new ObjectManager($this); + $this->urlBuilder = $this->getMockForAbstractClass(\Magento\Framework\UrlInterface::class); + } + + /** + * @param array $data + * @param array $dataSourceItems + * @param array $expectedDataSourceItems + * @param string $expectedUrlPath + * @param array $expectedUrlParam + * + * @dataProvider getPrepareDataSourceDataProvider + * @return void + */ + public function testPrepareDataSource( + $data, + $dataSourceItems, + $expectedDataSourceItems, + $expectedUrlPath, + $expectedUrlParam + ) { + $contextMock = $this->getMockBuilder(\Magento\Framework\View\Element\UiComponent\ContextInterface::class) + ->getMockForAbstractClass(); + $processor = $this->getMockBuilder(\Magento\Framework\View\Element\UiComponent\Processor::class) + ->disableOriginalConstructor() + ->getMock(); + $contextMock->expects($this->never())->method('getProcessor')->willReturn($processor); + $this->model = $this->objectManager->getObject( + ViewAction::class, + [ + 'urlBuilder' => $this->urlBuilder, + 'data' => $data, + 'context' => $contextMock, + ] + ); + + $this->urlBuilder->expects($this->once()) + ->method('getUrl') + ->with($expectedUrlPath, $expectedUrlParam) + ->willReturn('url'); + + $dataSource = [ + 'data' => [ + 'items' => $dataSourceItems + ] + ]; + $dataSource = $this->model->prepareDataSource($dataSource); + $this->assertEquals($expectedDataSourceItems, $dataSource['data']['items']); + } + + /** + * Data provider for testPrepareDataSource + * @return array + */ + public function getPrepareDataSourceDataProvider() + { + return [ + [ + ['name' => 'itemName', 'config' => []], + [['itemName' => '', 'entity_id' => 1]], + [['itemName' => ['view' => ['href' => 'url', 'label' => __('View')]], 'entity_id' => 1]], + '#', + ['id' => 1] + ], + [ + ['name' => 'itemName', 'config' => [ + 'viewUrlPath' => 'url_path', + 'urlEntityParamName' => 'theme_id', + 'indexField' => 'theme_id'] + ], + [['itemName' => '', 'theme_id' => 2]], + [['itemName' => ['view' => ['href' => 'url', 'label' => __('View')]], 'theme_id' => 2]], + 'url_path', + ['theme_id' => 2] + ] + ]; + } +} diff --git a/app/code/Magento/Theme/Ui/Component/Listing/Column/ViewAction.php b/app/code/Magento/Theme/Ui/Component/Listing/Column/ViewAction.php new file mode 100644 index 0000000000000..774d5bab660af --- /dev/null +++ b/app/code/Magento/Theme/Ui/Component/Listing/Column/ViewAction.php @@ -0,0 +1,77 @@ +urlBuilder = $urlBuilder; + parent::__construct($context, $uiComponentFactory, $components, $data); + } + + /** + * Prepare Theme Data Source + * + * @param array $dataSource + * @return array + */ + public function prepareDataSource(array $dataSource) : array + { + if (isset($dataSource['data']['items'])) { + foreach ($dataSource['data']['items'] as & $item) { + $indexField = $this->getData('config/indexField') ?: 'entity_id'; + if (isset($item[$indexField])) { + $viewUrlPath = $this->getData('config/viewUrlPath') ?: '#'; + $urlEntityParamName = $this->getData('config/urlEntityParamName') ?: 'id'; + $item[$this->getData('name')] = [ + 'view' => [ + 'href' => $this->urlBuilder->getUrl( + $viewUrlPath, + [ + $urlEntityParamName => $item[$indexField] + ] + ), + 'label' => __('View') + ] + ]; + } + } + } + + return $dataSource; + } +} diff --git a/app/code/Magento/Theme/Ui/Component/Theme/DataProvider/SearchResult.php b/app/code/Magento/Theme/Ui/Component/Theme/DataProvider/SearchResult.php new file mode 100644 index 0000000000000..696b38a71761a --- /dev/null +++ b/app/code/Magento/Theme/Ui/Component/Theme/DataProvider/SearchResult.php @@ -0,0 +1,53 @@ + [ + 'theme_id' => 'main_table.theme_id', + 'theme_title' => 'main_table.theme_title', + 'theme_path' => 'main_table.theme_path', + 'parent_theme_title' => 'parent.theme_title', + ], + ]; + + /** + * Add area and type filters + * Join parent theme title + * + * @return $this + */ + protected function _initSelect() + { + parent::_initSelect(); + $this + ->addFieldToFilter('main_table.area', \Magento\Framework\App\Area::AREA_FRONTEND) + ->addFieldToFilter('main_table.type', ['in' => [ + \Magento\Framework\View\Design\ThemeInterface::TYPE_PHYSICAL, + \Magento\Framework\View\Design\ThemeInterface::TYPE_VIRTUAL, + ]]) + ; + + $this->getSelect()->joinLeft( + ['parent' => $this->getMainTable()], + 'main_table.parent_id = parent.theme_id', + ['parent_theme_title' => 'parent.theme_title'] + ); + + return $this; + } +} diff --git a/app/code/Magento/Theme/etc/di.xml b/app/code/Magento/Theme/etc/di.xml index c20184fec6bc4..55119f3449389 100644 --- a/app/code/Magento/Theme/etc/di.xml +++ b/app/code/Magento/Theme/etc/di.xml @@ -108,6 +108,7 @@ Magento\Theme\Model\ResourceModel\Design\Config\Grid\Collection + Magento\Theme\Ui\Component\Theme\DataProvider\SearchResult @@ -273,4 +274,11 @@ Magento\Theme\Model\ResourceModel\Theme\Collection + + + theme + Magento\Theme\Model\ResourceModel\Theme + theme_id + + diff --git a/app/code/Magento/Theme/i18n/en_US.csv b/app/code/Magento/Theme/i18n/en_US.csv index 2b8765c36d24a..50551724018c3 100644 --- a/app/code/Magento/Theme/i18n/en_US.csv +++ b/app/code/Magento/Theme/i18n/en_US.csv @@ -185,3 +185,6 @@ Settings,Settings "2 columns with left bar","2 columns with left bar" "2 columns with right bar","2 columns with right bar" "3 columns","3 columns" +ID,ID +View,View +Action,Action diff --git a/app/code/Magento/Theme/view/adminhtml/layout/adminhtml_system_design_theme_index.xml b/app/code/Magento/Theme/view/adminhtml/layout/adminhtml_system_design_theme_index.xml index 7bbdc526a6143..3b377899b9199 100644 --- a/app/code/Magento/Theme/view/adminhtml/layout/adminhtml_system_design_theme_index.xml +++ b/app/code/Magento/Theme/view/adminhtml/layout/adminhtml_system_design_theme_index.xml @@ -6,11 +6,9 @@ */ --> - - - + diff --git a/app/code/Magento/Theme/view/adminhtml/ui_component/design_theme_listing.xml b/app/code/Magento/Theme/view/adminhtml/ui_component/design_theme_listing.xml new file mode 100644 index 0000000000000..bb46592070c7a --- /dev/null +++ b/app/code/Magento/Theme/view/adminhtml/ui_component/design_theme_listing.xml @@ -0,0 +1,89 @@ + + ++ + + design_theme_listing.design_theme_listing_data_source + + + + design_theme_columns + + design_theme_listing.design_theme_listing_data_source + + + + + + + Magento_Theme::theme + + + id + theme_id + + + + + + + + + + + + + + design_theme_listing.design_theme_listing.design_theme_columns.actions + applyAction + + view + ${ $.$data.rowIndex } + + + + + + + textRange + + asc + false + + + + + text + + + + + + text + + + + + + text + + + + + + + adminhtml/system_design_theme/edit + id + + + + theme_id + + + + diff --git a/dev/tests/functional/tests/app/Magento/Widget/Test/Handler/Widget/Curl.php b/dev/tests/functional/tests/app/Magento/Widget/Test/Handler/Widget/Curl.php index 7077def5a4a25..1a024eefe162d 100644 --- a/dev/tests/functional/tests/app/Magento/Widget/Test/Handler/Widget/Curl.php +++ b/dev/tests/functional/tests/app/Magento/Widget/Test/Handler/Widget/Curl.php @@ -244,14 +244,22 @@ protected function preparePagesGroup(array $widgetInstancePageGroup) */ protected function getThemeId($title) { - $filter = base64_encode('theme_title=' . $title); - $url = $_ENV['app_backend_url'] . 'admin/system_design_theme/grid/filter/' . $filter; + $url = $_ENV['app_backend_url'] . 'mui/index/render/'; + $data = [ + 'namespace' => 'design_theme_listing', + 'filters' => [ + 'placeholder' => true, + 'theme_title' => $title + ], + 'isAjax' => true + ]; $curl = new BackendDecorator(new CurlTransport(), $this->_configuration); - $curl->write($url, [], CurlInterface::GET); + + $curl->write($url, $data, CurlInterface::POST); $response = $curl->read(); $curl->close(); - preg_match('/