custom/plugins/MaxiaListingVariants6/src/Service/ConfigService.php line 74

Open in your IDE?
  1. <?php
  2. namespace Maxia\MaxiaListingVariants6\Service;
  3. use Shopware\Core\Content\Category\CategoryEntity;
  4. use Shopware\Core\Framework\DataAbstractionLayer\EntityRepository;
  5. use Shopware\Core\Framework\DataAbstractionLayer\Search\Criteria;
  6. use Shopware\Core\Framework\Struct\Struct;
  7. use Maxia\MaxiaListingVariants6\Config\BaseConfig;
  8. use Maxia\MaxiaListingVariants6\Config\ProductConfig;
  9. use Maxia\MaxiaListingVariants6\Config\PropertyGroupConfig;
  10. use Maxia\MaxiaListingVariants6\MaxiaListingVariants6;
  11. use Shopware\Core\Content\Cms\Aggregate\CmsSlot\CmsSlotEntity;
  12. use Shopware\Core\Content\Product\ProductEntity;
  13. use Shopware\Core\Content\Property\PropertyGroupEntity;
  14. use Shopware\Core\System\SalesChannel\SalesChannelContext;
  15. use Shopware\Core\System\SystemConfig\SystemConfigService;
  16. use Symfony\Component\HttpFoundation\RequestStack;
  17. class ConfigService
  18. {
  19.     /** @var string */
  20.     private $namespace;
  21.     /** @var SystemConfigService */
  22.     private $systemConfig;
  23.     /** @var ProductConfig */
  24.     private $baseConfig;
  25.     /** @var RequestStack */
  26.     private $requestStack;
  27.     /** @var EntityRepository */
  28.     private $categoryRepository;
  29.     public function __construct(
  30.         string $namespace,
  31.         SystemConfigService $systemConfig,
  32.         RequestStack $requestStack,
  33.         /*EntityRepository*/ $categoryRepository
  34.     ) {
  35.         $this->namespace $namespace;
  36.         $this->systemConfig $systemConfig;
  37.         $this->requestStack $requestStack;
  38.         $this->categoryRepository $categoryRepository;
  39.     }
  40.     /**
  41.      * @return SystemConfigService
  42.      */
  43.     public function getSystemConfig(): SystemConfigService
  44.     {
  45.         return $this->systemConfig;
  46.     }
  47.     /**
  48.      * Returns the plugin configuration as array, with defaults.
  49.      *
  50.      * @param SalesChannelContext|int $context
  51.      * @return BaseConfig
  52.      */
  53.     public function getBaseConfig($context): BaseConfig
  54.     {
  55.         if ($this->baseConfig === null) {
  56.             $config $this->systemConfig->get(
  57.                 $this->namespace,
  58.                 $context instanceof SalesChannelContext
  59.                     $context->getSalesChannel()->getId()
  60.                     : $context
  61.             );
  62.             $struct = new BaseConfig();
  63.             $struct->assign($config);
  64.             $struct->setDisplayParentSupported(
  65.                 (new \ReflectionClass(ProductEntity::class))->hasMethod('getVariantListingConfig')
  66.             );
  67.             $this->baseConfig $struct;
  68.         }
  69.         return $this->baseConfig;
  70.     }
  71.     /**
  72.      * Returns the extended property group config.
  73.      *
  74.      * @param PropertyGroupEntity $groupEntity
  75.      * @param SalesChannelContext $context
  76.      * @return PropertyGroupConfig
  77.      */
  78.     public function getPropertyGroupConfig(PropertyGroupEntity $groupEntitySalesChannelContext $context) : PropertyGroupConfig
  79.     {
  80.         $groupConfig PropertyGroupConfig::createFromCustomFields(
  81.             $groupEntity->getTranslation('customFields'),
  82.             MaxiaListingVariants6::CUSTOM_FIELD_PREFIX.'_property'
  83.         );
  84.         if (!$groupConfig->getMaxEntries()) {
  85.             $groupConfig->setMaxEntries($this->getBaseConfig($context)->getMaxEntries() ?? 4);
  86.         }
  87.         $groupConfig->setTotalEntries($groupEntity->getOptions() ? $groupEntity->getOptions()->count() : null);
  88.         return $groupConfig;
  89.     }
  90.     /**
  91.      * Returns the product variant config for a cms slot.
  92.      *
  93.      * @param CmsSlotEntity $slot
  94.      * @param SalesChannelContext $context
  95.      * @return ProductConfig
  96.      */
  97.     protected function getCmsSlotConfig(CmsSlotEntity $slotSalesChannelContext $context) : ProductConfig
  98.     {
  99.         $productConfig ProductConfig::createFromCustomFields(
  100.             $slot->getCustomFields() ?: [],
  101.             MaxiaListingVariants6::CUSTOM_FIELD_PREFIX.'_cms_block'
  102.         );
  103.         $category $this->getCurrentCategory($context);
  104.         if ($category && $category->getSlotConfig() && isset($category->getSlotConfig()[$slot->getId()])) {
  105.             $slotConfig $category->getSlotConfig()[$slot->getId()];
  106.             if (isset($slotConfig['maxiaListingVariants'])) {
  107.                 $value = isset($slotConfig['maxiaListingVariants']['value'])
  108.                     ? $slotConfig['maxiaListingVariants']['value']
  109.                     : $slotConfig['maxiaListingVariants'];
  110.                 $categoryConfig ProductConfig::createFromCustomFields(
  111.                     $value,
  112.                     MaxiaListingVariants6::CUSTOM_FIELD_PREFIX.'_cms_block'
  113.                 );
  114.                 $productConfig $this->mergeStruct(ProductConfig::class, $productConfig$categoryConfig);
  115.             }
  116.         }
  117.         return $this->mergeStruct(ProductConfig::class, $this->getBaseConfig($context), $productConfig);
  118.     }
  119.     /**
  120.      * Returns the product variant config for a product.
  121.      *
  122.      * @param ProductEntity $product
  123.      * @param CmsSlotEntity|null $slot
  124.      * @param SalesChannelContext $context
  125.      * @return ProductConfig
  126.      */
  127.     public function getProductConfig(ProductEntity $productCmsSlotEntity $slot nullSalesChannelContext $context) : ProductConfig
  128.     {
  129.         $baseConfig $slot !== null
  130.             $this->getCmsSlotConfig($slot$context)
  131.             : $this->getBaseConfig($context);
  132.         $productConfig ProductConfig::createFromCustomFields(
  133.             $product->getCustomFields() ?: [],
  134.             MaxiaListingVariants6::CUSTOM_FIELD_PREFIX.'_product'
  135.         );
  136.         $newConfig $this->mergeStruct(ProductConfig::class, $baseConfig$productConfig);
  137.         if ($baseConfig->getDisplayMode() === 'none') {
  138.             $newConfig->setDisplayMode('none');
  139.         }
  140.         return $newConfig;
  141.     }
  142.     /**
  143.      * @param $type
  144.      * @param Struct $a
  145.      * @param Struct $b
  146.      * @return mixed
  147.      */
  148.     public function mergeStruct($typeStruct $aStruct $b)
  149.     {
  150.         /** @var Struct $result */
  151.         $result = new $type;
  152.         if (!$result instanceof Struct) {
  153.             throw new \InvalidArgumentException("a struct is required");
  154.         }
  155.         $fillKeys array_keys($result->getVars());
  156.         $result->assign(array_filter($a->getVars(), function ($key) use ($fillKeys) {
  157.             return in_array($key$fillKeystrue);
  158.         }, ARRAY_FILTER_USE_KEY));
  159.         foreach ($b->getVars() as $key => $value) {
  160.             if ($value !== null && $value !== 'inherited' && in_array($key$fillKeystrue)) {
  161.                 $result->assign([$key => $value]);
  162.             }
  163.         }
  164.         return $result;
  165.     }
  166.     /**
  167.      * Check if the given property group should be displayed by config.
  168.      *
  169.      * @param ProductConfig $config
  170.      * @param PropertyGroupEntity $group
  171.      * @param int $index
  172.      * @return bool
  173.      */
  174.     public function checkDisplayMode(ProductConfig $configPropertyGroupEntity $groupint $index) : bool
  175.     {
  176.         if ($config->getDisplayMode() === 'all') {
  177.             return true;
  178.         }
  179.         if ($config->getDisplayMode() === 'none') {
  180.             return false;
  181.         }
  182.         if ($config->getDisplayMode() === 'selected') {
  183.             if (!$config->getRestrictedProperties()) {
  184.                 return true;
  185.             }
  186.             return in_array($group->getId(), $config->getRestrictedProperties(), false);
  187.         }
  188.         // property_1, property_2, property_1_2, ...
  189.         if (!preg_match('/^index_(\d)_?(\d)?$/'$config->getDisplayMode(), $matches)) {
  190.             return false;
  191.         }
  192.         $allowedIndexes = [(int)$matches[1]];
  193.         if (isset($matches[2])) {
  194.             $allowedIndexes[] = (int)$matches[2];
  195.         }
  196.         if (in_array($index 1$allowedIndexes)) {
  197.             return true;
  198.         }
  199.         return false;
  200.     }
  201.     /**
  202.      * @param SalesChannelContext $context
  203.      * @return CategoryEntity|null
  204.      */
  205.     protected function getCurrentCategory(SalesChannelContext $context)
  206.     {
  207.         static $category false;
  208.         if ($category === false) {
  209.             $request $this->requestStack->getMainRequest();
  210.             if ($request->query->get('navigationId')) {
  211.                 $navigationId $request->query->get('navigationId'$context->getSalesChannel()->getNavigationCategoryId());
  212.             } else {
  213.                 $navigationId $request->attributes->get('navigationId'$context->getSalesChannel()->getNavigationCategoryId());
  214.             }
  215.             if ($navigationId) {
  216.                 $result $this->categoryRepository->search(new Criteria([$navigationId]), $context->getContext());
  217.                 if ($result->first()) {
  218.                     $category $result->first();
  219.                 } else {
  220.                     $category null;
  221.                 }
  222.             }
  223.         }
  224.         return $category;
  225.     }
  226. }