<?php declare(strict_types=1);
namespace Nds\RecipeManager;
use Doctrine\DBAL\Connection;
use Shopware\Core\Framework\Plugin;
use Shopware\Core\Framework\Context;
use Shopware\Core\Framework\Uuid\Uuid;
use Nds\RecipeManager\Util\Lifecycle\ActivateDeactivate;
use Shopware\Core\Framework\Plugin\Context\UpdateContext;
use Shopware\Core\Framework\Plugin\Context\InstallContext;
use Nds\RecipeManager\Core\Content\Recipe\RecipeDefinition;
use Shopware\Core\Framework\Plugin\Context\ActivateContext;
use Symfony\Component\DependencyInjection\ContainerBuilder;
use Shopware\Core\Framework\Plugin\Context\UninstallContext;
use Shopware\Core\Framework\Plugin\Context\DeactivateContext;
use Shopware\Core\Framework\DataAbstractionLayer\Search\Criteria;
use Shopware\Core\Content\Media\Aggregate\MediaFolder\MediaFolderEntity;
use Shopware\Core\Framework\DataAbstractionLayer\EntityRepositoryInterface;
use Shopware\Core\Framework\DataAbstractionLayer\Search\Filter\MultiFilter;
use Shopware\Core\Framework\DataAbstractionLayer\Search\Filter\EqualsFilter;
class NdsRecipeManager extends Plugin
{
private ?ActivateDeactivate $activateDeactivate = null;
public function setActivateDeactivate(ActivateDeactivate $activateDeactivate): void
{
$this->activateDeactivate = $activateDeactivate;
}
public function build(ContainerBuilder $container): void
{
parent::build($container);
}
public function install(InstallContext $installContext): void
{
$this->createRecipeMediaFolder($installContext->getContext());
$this->setDefaultThumbnailSize($installContext->getContext());
$this->createRecipeCmsListingPage($installContext->getContext());
}
public function activate(ActivateContext $activateContext): void
{
$this->activateDeactivate->activate($activateContext->getContext());
parent::activate($activateContext);
}
public function update(UpdateContext $updateContext): void
{
parent::update($updateContext);
}
public function deactivate(DeactivateContext $deactivateContext): void
{
parent::deactivate($deactivateContext);
}
public function uninstall(UninstallContext $uninstallContext): void
{
parent::uninstall($uninstallContext);
if ($uninstallContext->keepUserData()) {
return;
}
// Drop all tables from Plugin
$connection = $this->container->get(Connection::class);
// Remove m_to_m first
$connection->executeStatement('DROP TABLE IF EXISTS `nds_rcp_recipe_category`');
$connection->executeStatement('DROP TABLE IF EXISTS `nds_rcp_recipe_tag`');
$connection->executeStatement('DROP TABLE IF EXISTS `nds_rcp_recipe_ingredient`');
$connection->executeStatement('DROP TABLE IF EXISTS `nds_rcp_related`');
$connection->executeStatement('DROP TABLE IF EXISTS `nds_rcp_recipe_difficulty`');
$connection->executeStatement('DROP TABLE IF EXISTS `nds_rcp_timeunit`');
$connection->executeStatement('DROP TABLE IF EXISTS `nds_rcp_recipe_media`');
// Get rid of all translations
$connection->executeStatement('DROP TABLE IF EXISTS `nds_rcp_category_translation`');
$connection->executeStatement('DROP TABLE IF EXISTS `nds_rcp_tag_translation`');
$connection->executeStatement('DROP TABLE IF EXISTS `nds_rcp_ingredient_translation`');
$connection->executeStatement('DROP TABLE IF EXISTS `nds_rcp_difficulty_translation`');
$connection->executeStatement('DROP TABLE IF EXISTS `nds_rcp_unit_translation`');
$connection->executeStatement('DROP TABLE IF EXISTS `nds_rcp_recipe_translation`');
// Delete all main entities
$connection->executeStatement('DROP TABLE IF EXISTS `nds_rcp_recipe`');
$connection->executeStatement('DROP TABLE IF EXISTS `nds_rcp_difficulty`');
$connection->executeStatement('DROP TABLE IF EXISTS `nds_rcp_ingredient`');
$connection->executeStatement('DROP TABLE IF EXISTS `nds_rcp_unit`');
$connection->executeStatement('DROP TABLE IF EXISTS `nds_rcp_tag`');
$connection->executeStatement('DROP TABLE IF EXISTS `nds_rcp_category`');
// Delete all plugin config rows and seo templates
$connection->executeStatement("DELETE FROM `system_config` WHERE `configuration_key` LIKE 'NdsRecipeManager%';");
$connection->executeStatement("DELETE FROM `seo_url_template` WHERE `route_name` LIKE 'rcp.frontend%';");
$connection->executeStatement("DELETE FROM `seo_url` WHERE `route_name` LIKE 'rcp.frontend%';");
// Delete all media folders
$this->deleteMediaFolder($uninstallContext->getContext());
$this->deleteDefaultMediaFolder($uninstallContext->getContext());
// Delete cms pages
$this->deleteCmsPages($uninstallContext->getContext());
}
public function createRecipeCmsListingPage(Context $context): void
{
$cmsPageRepository = $this->container->get('cms_page.repository');
$cmsPage = [
[
'id' => 'b008af97ec5e43a482ce4335f74f4a53',
'type' => 'page',
'translations' => [
'de-DE' => [
'name' => 'Rezeptliste',
],
'en-GB' => [
'name' => 'Recipes list page',
],
],
'sections' => [
[
'id' => Uuid::randomHex(),
'type' => 'default',
'position' => 0,
'name' => 'Recipe List',
'blocks' => [
[
'position' => 1,
'type' => 'recipe-list-block',
'name' => 'Recipe List',
'slots' => [
['type' => 'recipe-list', 'slot' => 'recipeList'],
],
],
],
],
],
],
];
$cmsPageRepository->upsert($cmsPage, $context);
}
public function createRecipeMediaFolder(Context $context): void
{
$this->deleteDefaultMediaFolder($context);
// Create Folder
$mediaDefaultFolderRepository = $this->container->get('media_default_folder.repository');
$mediaDefaultFolderRepository->create([
[
'id' => Uuid::randomHex(),
'entity' => RecipeDefinition::ENTITY_NAME,
'associationFields' => [],
'folder' => [
'id' => Uuid::randomHex(),
'useParentConfiguration' => false,
'name' => 'Recipes Manager Media',
'configuration' => [
'createThumbnails' => true,
'thumbnailQuality' => 80,
'keepAspectRatio' => true,
],
],
],
], $context);
}
protected function deleteMediaFolder(Context $context): void
{
$criteria = new Criteria();
$criteria->addFilter(new EqualsFilter('name', 'Recipes Manager Media'));
/** @var EntityRepositoryInterface $mediaFolderRepository */
$mediaFolderRepository = $this->container->get('media_folder.repository');
$mediaFolderRepository->search($criteria, $context);
$mediaFolderIds = $mediaFolderRepository->searchIds($criteria, $context)->getIds();
if (! empty($mediaFolderIds)) {
$ids = \array_map(static function ($id) {
return ['id' => $id];
}, $mediaFolderIds);
$mediaFolderRepository->delete($ids, $context);
}
}
protected function deleteDefaultMediaFolder(Context $context): void
{
$criteria = new Criteria();
$criteria->addFilter(new EqualsFilter('entity', RecipeDefinition::ENTITY_NAME));
/** @var EntityRepositoryInterface $mediaFolderRepository */
$mediaFolderRepository = $this->container->get('media_default_folder.repository');
$mediaFolderIds = $mediaFolderRepository->searchIds($criteria, $context)->getIds();
if (! empty($mediaFolderIds)) {
$ids = \array_map(static function ($id) {
return ['id' => $id];
}, $mediaFolderIds);
$mediaFolderRepository->delete($ids, $context);
}
}
protected function deleteCmsPages(Context $context): void
{
$cmsPageRepository = $this->container->get('cms_page.repository');
$criteria = new Criteria();
$criteria->addFilter(
new MultiFilter(
MultiFilter::CONNECTION_OR,
[
new EqualsFilter('name', 'Rezeptliste'),
]
)
);
$cmsPageRepository->searchIds($criteria, $context);
$pageIds = $cmsPageRepository->searchIds($criteria, $context)->getIds();
if (! empty($pageIds)) {
$ids = \array_map(static function ($id) {
return ['id' => $id];
}, $pageIds);
$cmsPageRepository->delete($ids, $context);
}
}
protected function setDefaultThumbnailSize(Context $context): void
{
// Get default thumbnail size IDs
$mediaThumbnailSizeRepository = $this->container->get('media_thumbnail_size.repository');
$mediaThumbnailSizeIds = $mediaThumbnailSizeRepository->search(new Criteria(), $context)->getIds();
// Get recipe media folder
$criteria = new Criteria();
$criteria->addFilter(new EqualsFilter('name', 'Recipes Manager Media'));
/** @var EntityRepositoryInterface $mediaFolderRepository */
$mediaFolderRepository = $this->container->get('media_folder.repository');
$mediaFolderRepository->search($criteria, $context);
/** @var MediaFolderEntity $mediaFolder */
$mediaFolder = $mediaFolderRepository->search($criteria, $context)->getEntities()->first();
$folderConfigurationId = $mediaFolder->getConfigurationId();
$connection = $this->container->get(Connection::class);
foreach ($mediaThumbnailSizeIds as $mediaThumbnailSizeId) {
$connection->executeStatement('
INSERT INTO `media_folder_configuration_media_thumbnail_size` (`media_folder_configuration_id`, `media_thumbnail_size_id`)
VALUES (UNHEX(:folderConfigurationId), UNHEX(:thumbnailSizeId))
', [
'folderConfigurationId' => $folderConfigurationId,
'thumbnailSizeId' => $mediaThumbnailSizeId,
]);
}
}
}