resource = $resource; $this->pageFactory = $pageFactory; $this->pageCollectionFactory = $pageCollectionFactory; $this->searchResultsFactory = $searchResultsFactory; $this->dataObjectHelper = $dataObjectHelper; $this->dataPageFactory = $dataPageFactory; $this->dataObjectProcessor = $dataObjectProcessor; $this->storeManager = $storeManager; $this->collectionProcessor = $collectionProcessor ?: $this->getCollectionProcessor(); $this->identityMap = $identityMap ?? ObjectManager::getInstance() ->get(IdentityMap::class); $this->hydrator = $hydrator ?: ObjectManager::getInstance() ->get(HydratorInterface::class); $this->routeConfig = $routeConfig ?? ObjectManager::getInstance() ->get(Config::class); } /** * Validate new layout update values. * * @param PageInterface $page * @return void * @throws \InvalidArgumentException */ private function validateLayoutUpdate(PageInterface $page): void { //Persisted data $oldData = null; if ($page->getId() && $page instanceof Page) { $oldData = $page->getOrigData(); } //Custom layout update can be removed or kept as is. if ($page->getCustomLayoutUpdateXml() && ( !$oldData || $page->getCustomLayoutUpdateXml() !== $oldData[Data\PageInterface::CUSTOM_LAYOUT_UPDATE_XML] ) ) { throw new \InvalidArgumentException('Custom layout updates must be selected from a file'); } if ($page->getLayoutUpdateXml() && (!$oldData || $page->getLayoutUpdateXml() !== $oldData[Data\PageInterface::LAYOUT_UPDATE_XML]) ) { throw new \InvalidArgumentException('Custom layout updates must be selected from a file'); } } /** * Save Page data * * @param PageInterface|Page $page * @return Page * @throws CouldNotSaveException */ public function save(PageInterface $page) { try { $pageId = $page->getId(); if ($pageId && !($page instanceof Page && $page->getOrigData())) { $page = $this->hydrator->hydrate($this->getById($pageId), $this->hydrator->extract($page)); } if ($page->getStoreId() === null) { $storeId = $this->storeManager->getStore()->getId(); $page->setStoreId($storeId); } $this->validateLayoutUpdate($page); $this->validateRoutesDuplication($page); $this->resource->save($page); $this->identityMap->add($page); } catch (LocalizedException $exception) { throw new CouldNotSaveException( __('Could not save the page: %1', $exception->getMessage()), $exception ); } catch (\Throwable $exception) { throw new CouldNotSaveException( __('Could not save the page: %1', __('Something went wrong while saving the page.')), $exception ); } return $page; } /** * Load Page data by given Page Identity * * @param string $pageId * @return Page * @throws NoSuchEntityException */ public function getById($pageId) { $page = $this->pageFactory->create(); $page->load($pageId); if (!$page->getId()) { throw new NoSuchEntityException(__('The CMS page with the "%1" ID doesn\'t exist.', $pageId)); } $this->identityMap->add($page); return $page; } /** * Load Page data collection by given search criteria * * @SuppressWarnings(PHPMD.CyclomaticComplexity) * @SuppressWarnings(PHPMD.NPathComplexity) * @param SearchCriteriaInterface $criteria * @return PageSearchResultsInterface */ public function getList(SearchCriteriaInterface $criteria) { $collection = $this->pageCollectionFactory->create(); $this->collectionProcessor->process($criteria, $collection); $searchResults = $this->searchResultsFactory->create(); $searchResults->setSearchCriteria($criteria); $searchResults->setItems($collection->getItems()); $searchResults->setTotalCount($collection->getSize()); return $searchResults; } /** * Delete Page * * @param PageInterface $page * @return bool * @throws CouldNotDeleteException */ public function delete(PageInterface $page) { try { $this->resource->delete($page); $this->identityMap->remove($page->getId()); } catch (\Exception $exception) { throw new CouldNotDeleteException( __('Could not delete the page: %1', $exception->getMessage()) ); } return true; } /** * Delete Page by given Page Identity * * @param string $pageId * @return bool * @throws CouldNotDeleteException * @throws NoSuchEntityException */ public function deleteById($pageId) { return $this->delete($this->getById($pageId)); } /** * Retrieve collection processor * * @deprecated 102.0.0 * @return CollectionProcessorInterface */ private function getCollectionProcessor() { if (!$this->collectionProcessor) { // phpstan:ignore "Class Magento\Cms\Model\Api\SearchCriteria\PageCollectionProcessor not found." $this->collectionProcessor = ObjectManager::getInstance() ->get(PageCollectionProcessor::class); } return $this->collectionProcessor; } /** * Checks that page identifier doesn't duplicate existed routes * * @param PageInterface $page * @return void * @throws CouldNotSaveException */ private function validateRoutesDuplication($page): void { if ($this->routeConfig->getRouteByFrontName($page->getIdentifier(), 'frontend')) { throw new CouldNotSaveException( __('The value specified in the URL Key field would generate a URL that already exists.') ); } } }