diff --git a/vendor/magento/module-visual-merchandiser/Plugin/Catalog/Model/ResourceModel/Product/RankCategoryProductPositions.php b/vendor/magento/module-visual-merchandiser/Plugin/Catalog/Model/ResourceModel/Product/RankCategoryProductPositions.php new file mode 100644 index 00000000000..20a862a347b --- /dev/null +++ b/vendor/magento/module-visual-merchandiser/Plugin/Catalog/Model/ResourceModel/Product/RankCategoryProductPositions.php @@ -0,0 +1,104 @@ +categoryResourceModel = $categoryResourceModel; + $this->positionResolver = $positionResolver; + $this->resourceConnection = $resourceConnection; + } + + /** + * Rank category product positions. + * + * @param CategoryProductLink $categoryProductLink + * @param callable $proceed + * @param ProductInterface $product + * @param array $insertLinks + * @param bool $insert + * @return array + * + * @SuppressWarnings(PHPMD.UnusedFormalParameter) + */ + public function aroundUpdateCategoryLinks( + CategoryProductLink $categoryProductLink, + callable $proceed, + ProductInterface $product, + array $insertLinks, + $insert = false + ): array { + foreach ($insertLinks as $link) { + $this->resourceConnection->getConnection()->insertOnDuplicate( + $this->categoryResourceModel->getCategoryProductTable(), + $this->getCategoryProductPositions((int) $product->getId(), (int) $link['category_id']), + ['position'] + ); + } + + return array_column($insertLinks, 'category_id'); + } + + /** + * Retrieve and prepare category product positions array. + * + * @param int $productId + * @param int $categoryId + * @return array + */ + private function getCategoryProductPositions(int $productId, int $categoryId): array + { + $categoryProductPositions = []; + $existingCategoryProductPositions = array_flip($this->positionResolver->getPositions((int) $categoryId)); + array_unshift($existingCategoryProductPositions, $productId); + + foreach (array_flip($existingCategoryProductPositions) as $productId => $productPosition) { + $categoryProductPositions[] = [ + 'category_id' => (int) $categoryId, + 'product_id' => $productId, + 'position' => $productPosition, + ]; + } + + return $categoryProductPositions; + } +} diff --git a/vendor/magento/module-visual-merchandiser/etc/adminhtml/di.xml b/vendor/magento/module-visual-merchandiser/etc/adminhtml/di.xml index 9b581da080b..cdbafab69c4 100644 --- a/vendor/magento/module-visual-merchandiser/etc/adminhtml/di.xml +++ b/vendor/magento/module-visual-merchandiser/etc/adminhtml/di.xml @@ -15,4 +15,7 @@ + + +