/**
  * @param \Magento\Catalog\Model\Product $product
  * @return void
  */
 protected function processDynamicOptionsData(\Magento\Catalog\Model\Product $product)
 {
     if ((int) $product->getPriceType() !== \Magento\Bundle\Model\Product\Price::PRICE_TYPE_DYNAMIC) {
         return;
     }
     if ($product->getOptionsReadonly()) {
         return;
     }
     $product->setCanSaveCustomOptions(true);
     $customOptions = $product->getProductOptions();
     if (!$customOptions) {
         return;
     }
     foreach (array_keys($customOptions) as $key) {
         $customOptions[$key]['is_delete'] = 1;
     }
     $newOptions = $product->getOptions();
     foreach ($customOptions as $customOptionData) {
         if ((bool) $customOptionData['is_delete']) {
             continue;
         }
         $customOption = $this->customOptionFactory->create(['data' => $customOptionData]);
         $customOption->setProductSku($product->getSku());
         $customOption->setOptionId(null);
         $newOptions[] = $customOption;
     }
     $product->setOptions($newOptions);
 }
Пример #2
0
 /**
  * @param array $options
  * @param \Magento\Catalog\Model\Product $product
  * @return \Magento\Catalog\Api\Data\ProductCustomOptionInterface[]
  */
 protected function prepareOptions($options, $product)
 {
     $preparedOptions = [];
     if (!$this->customOptionFactory) {
         $this->customOptionFactory = $this->objectManager->create('Magento\\Catalog\\Api\\Data\\ProductCustomOptionInterfaceFactory');
     }
     foreach ($options as $option) {
         $option = $this->customOptionFactory->create(['data' => $option]);
         $option->setProductSku($product->getSku());
         $preparedOptions[] = $option;
     }
     return $preparedOptions;
 }
 protected function setUp()
 {
     $this->objectManager = new ObjectManager($this);
     $this->productLinkFactoryMock = $this->getMockBuilder(ProductLinkInterfaceFactory::class)->disableOriginalConstructor()->getMock();
     $this->productRepositoryMock = $this->getMockBuilder(ProductRepository::class)->disableOriginalConstructor()->getMock();
     $this->requestMock = $this->getMockBuilder(RequestInterface::class)->setMethods(['getPost'])->getMockForAbstractClass();
     $this->storeMock = $this->getMockBuilder(StoreInterface::class)->setMethods(['getWebsite'])->getMockForAbstractClass();
     $this->websiteMock = $this->getMockBuilder(WebsiteInterface::class)->getMockForAbstractClass();
     $this->storeManagerMock = $this->getMockBuilder(StoreManagerInterface::class)->getMockForAbstractClass();
     $this->dateFilterMock = $this->getMockBuilder(DateFilter::class)->disableOriginalConstructor()->getMock();
     $this->stockFilterMock = $this->getMockBuilder(StockDataFilter::class)->disableOriginalConstructor()->getMock();
     $this->productMock = $this->getMockBuilder(Product::class)->setMethods(['setData', 'addData', 'getId', 'setWebsiteIds', 'isLockedAttribute', 'lockAttribute', 'getAttributes', 'unlockAttribute', 'getOptionsReadOnly', 'setOptions', 'setCanSaveCustomOptions', '__sleep', '__wakeup', 'getSku', 'getProductLinks'])->disableOriginalConstructor()->getMock();
     $this->customOptionFactoryMock = $this->getMockBuilder(ProductCustomOptionInterfaceFactory::class)->disableOriginalConstructor()->setMethods(['create'])->getMock();
     $this->customOptionMock = $this->getMockBuilder(ProductCustomOptionInterface::class)->disableOriginalConstructor()->getMockForAbstractClass();
     $this->productLinksMock = $this->getMockBuilder(ProductLinks::class)->disableOriginalConstructor()->getMock();
     $this->customOptionFactoryMock->expects($this->any())->method('create')->with(['data' => ['is_delete' => false]])->willReturn($this->customOptionMock);
     $this->productLinksMock->expects($this->any())->method('initializeLinks')->willReturn($this->productMock);
     $this->helper = $this->objectManager->getObject(Helper::class, ['request' => $this->requestMock, 'storeManager' => $this->storeManagerMock, 'stockFilter' => $this->stockFilterMock, 'productLinks' => $this->productLinksMock, 'dateFilter' => $this->dateFilterMock, 'customOptionFactory' => $this->customOptionFactoryMock, 'productLinkFactory' => $this->productLinkFactoryMock, 'productRepository' => $this->productRepositoryMock]);
 }
Пример #4
0
 /**
  * @covers \Magento\Catalog\Controller\Adminhtml\Product\Initialization\Helper::initialize
  * @SuppressWarnings(PHPMD.ExcessiveMethodLength)
  */
 public function testInitialize()
 {
     $this->websiteMock->expects($this->once())->method('getId')->willReturn($this->websiteId);
     $this->storeMock->expects($this->once())->method('getWebsite')->willReturn($this->websiteMock);
     $this->storeManagerMock->expects($this->once())->method('getStore')->with(true)->willReturn($this->storeMock);
     $this->customOptionMock->expects($this->once())->method('setProductSku');
     $this->customOptionMock->expects($this->once())->method('setOptionId');
     $optionsData = ['option1' => ['is_delete' => true, 'name' => 'name1', 'price' => 'price1'], 'option2' => ['is_delete' => false, 'name' => 'name1', 'price' => 'price1']];
     $productData = ['stock_data' => ['stock_data'], 'options' => $optionsData];
     $attributeNonDate = $this->getMockBuilder(\Magento\Catalog\Model\ResourceModel\Eav\Attribute::class)->disableOriginalConstructor()->getMock();
     $attributeDate = $this->getMockBuilder(\Magento\Catalog\Model\ResourceModel\Eav\Attribute::class)->disableOriginalConstructor()->getMock();
     $attributeNonDateBackEnd = $this->getMockBuilder(\Magento\Eav\Model\Entity\Attribute\Backend\DefaultBackend::class)->disableOriginalConstructor()->getMock();
     $attributeDateBackEnd = $this->getMockBuilder(\Magento\Eav\Model\Entity\Attribute\Backend\Datetime::class)->disableOriginalConstructor()->getMock();
     $attributeNonDate->expects($this->any())->method('getBackend')->willReturn($attributeNonDateBackEnd);
     $attributeDate->expects($this->any())->method('getBackend')->willReturn($attributeDateBackEnd);
     $this->productMock->expects($this->any())->method('getProductLinks')->willReturn([]);
     $attributeNonDateBackEnd->expects($this->any())->method('getType')->willReturn('non-datetime');
     $attributeDateBackEnd->expects($this->any())->method('getType')->willReturn('datetime');
     $attributesArray = [$attributeNonDate, $attributeDate];
     $useDefaults = ['attributeCode1', 'attributeCode2'];
     $this->requestMock->expects($this->at(0))->method('getPost')->with('product')->willReturn($productData);
     $this->requestMock->expects($this->at(1))->method('getPost')->with('use_default')->willReturn($useDefaults);
     $this->linkResolverMock->expects($this->once())->method('getLinks')->willReturn([]);
     $this->stockFilterMock->expects($this->once())->method('filter')->with(['stock_data'])->willReturn(['stock_data']);
     $this->storeManagerMock->expects($this->once())->method('hasSingleStore')->willReturn(true);
     $this->productMock->expects($this->once())->method('isLockedAttribute')->with('media')->willReturn(true);
     $this->productMock->expects($this->once())->method('unlockAttribute')->with('media');
     $this->productMock->expects($this->any())->method('getProductLinks')->willReturn([]);
     $this->productMock->expects($this->once())->method('lockAttribute')->with('media');
     $this->productMock->expects($this->once())->method('getAttributes')->willReturn($attributesArray);
     $productData['category_ids'] = [];
     $productData['website_ids'] = [];
     unset($productData['options']);
     $this->productMock->expects($this->once())->method('addData')->with($productData);
     $this->productMock->expects($this->once())->method('getSku')->willReturn('sku');
     $this->productMock->expects($this->once())->method('setWebsiteIds')->with([$this->websiteId]);
     $this->productMock->expects($this->any())->method('getOptionsReadOnly')->willReturn(false);
     $this->customOptionFactoryMock->expects($this->any())->method('create')->with(['data' => $optionsData['option2']])->willReturn($this->customOptionMock);
     $this->productMock->expects($this->once())->method('setOptions')->with([$this->customOptionMock]);
     $this->assertEquals($this->productMock, $this->helper->initialize($this->productMock));
 }
 /**
  * Initialize product before saving
  *
  * @param \Magento\Catalog\Model\Product $product
  * @return \Magento\Catalog\Model\Product
  * @SuppressWarnings(PHPMD.CyclomaticComplexity)
  * @SuppressWarnings(PHPMD.NPathComplexity)
  * @SuppressWarnings(PHPMD.ExcessiveMethodLength)
  */
 public function initialize(\Magento\Catalog\Model\Product $product)
 {
     $productData = (array) $this->request->getPost('product', []);
     unset($productData['custom_attributes']);
     unset($productData['extension_attributes']);
     if ($productData) {
         $stockData = isset($productData['stock_data']) ? $productData['stock_data'] : [];
         $productData['stock_data'] = $this->stockFilter->filter($stockData);
     }
     $productData = $this->normalize($productData);
     if (!empty($productData['is_downloadable'])) {
         $productData['product_has_weight'] = 0;
     }
     foreach (['category_ids', 'website_ids'] as $field) {
         if (!isset($productData[$field])) {
             $productData[$field] = [];
         }
     }
     foreach ($productData['website_ids'] as $websiteId => $checkboxValue) {
         if (!$checkboxValue) {
             unset($productData['website_ids'][$websiteId]);
         }
     }
     $wasLockedMedia = false;
     if ($product->isLockedAttribute('media')) {
         $product->unlockAttribute('media');
         $wasLockedMedia = true;
     }
     $dateFieldFilters = [];
     $attributes = $product->getAttributes();
     foreach ($attributes as $attrKey => $attribute) {
         if ($attribute->getBackend()->getType() == 'datetime') {
             if (array_key_exists($attrKey, $productData) && $productData[$attrKey] != '') {
                 $dateFieldFilters[$attrKey] = $this->dateFilter;
             }
         }
     }
     $inputFilter = new \Zend_Filter_Input($dateFieldFilters, [], $productData);
     $productData = $inputFilter->getUnescaped();
     $product->addData($productData);
     if ($wasLockedMedia) {
         $product->lockAttribute('media');
     }
     if ($this->storeManager->hasSingleStore()) {
         $product->setWebsiteIds([$this->storeManager->getStore(true)->getWebsite()->getId()]);
     }
     /**
      * Check "Use Default Value" checkboxes values
      */
     $useDefaults = (array) $this->request->getPost('use_default', []);
     foreach ($useDefaults as $attributeCode => $useDefaultState) {
         if ($useDefaultState) {
             $product->setData($attributeCode, null);
         }
     }
     $product = $this->setProductLinks($product);
     /**
      * Initialize product options
      */
     if (isset($productData['options']) && !$product->getOptionsReadonly()) {
         // mark custom options that should to fall back to default value
         $options = $this->mergeProductOptions($productData['options'], $this->request->getPost('options_use_default'));
         $customOptions = [];
         foreach ($options as $customOptionData) {
             if (empty($customOptionData['is_delete'])) {
                 $customOption = $this->customOptionFactory->create(['data' => $customOptionData]);
                 $customOption->setProductSku($product->getSku());
                 $customOption->setOptionId(null);
                 $customOptions[] = $customOption;
             }
         }
         $product->setOptions($customOptions);
     }
     $product->setCanSaveCustomOptions(!empty($productData['affect_product_custom_options']) && !$product->getOptionsReadonly());
     return $product;
 }
Пример #6
0
 /**
  * Initialize product before saving
  *
  * @param \Magento\Catalog\Model\Product $product
  * @return \Magento\Catalog\Model\Product
  * @SuppressWarnings(PHPMD.CyclomaticComplexity)
  * @SuppressWarnings(PHPMD.NPathComplexity)
  * @SuppressWarnings(PHPMD.ExcessiveMethodLength)
  */
 public function initialize(\Magento\Catalog\Model\Product $product)
 {
     $productData = $this->request->getPost('product');
     unset($productData['custom_attributes']);
     unset($productData['extension_attributes']);
     if ($productData) {
         $stockData = isset($productData['stock_data']) ? $productData['stock_data'] : [];
         $productData['stock_data'] = $this->stockFilter->filter($stockData);
     }
     foreach (['category_ids', 'website_ids'] as $field) {
         if (!isset($productData[$field])) {
             $productData[$field] = [];
         }
     }
     $wasLockedMedia = false;
     if ($product->isLockedAttribute('media')) {
         $product->unlockAttribute('media');
         $wasLockedMedia = true;
     }
     $dateFieldFilters = [];
     $attributes = $product->getAttributes();
     foreach ($attributes as $attrKey => $attribute) {
         if ($attribute->getBackend()->getType() == 'datetime') {
             if (array_key_exists($attrKey, $productData) && $productData[$attrKey] != '') {
                 $dateFieldFilters[$attrKey] = $this->dateFilter;
             }
         }
     }
     $inputFilter = new \Zend_Filter_Input($dateFieldFilters, [], $productData);
     $productData = $inputFilter->getUnescaped();
     $product->addData($productData);
     if ($wasLockedMedia) {
         $product->lockAttribute('media');
     }
     if ($this->storeManager->hasSingleStore()) {
         $product->setWebsiteIds([$this->storeManager->getStore(true)->getWebsite()->getId()]);
     }
     /**
      * Check "Use Default Value" checkboxes values
      */
     $useDefaults = $this->request->getPost('use_default');
     if ($useDefaults) {
         foreach ($useDefaults as $attributeCode) {
             $product->setData($attributeCode, false);
         }
     }
     $links = $this->request->getPost('links');
     $links = is_array($links) ? $links : [];
     $linkTypes = ['related', 'upsell', 'crosssell'];
     foreach ($linkTypes as $type) {
         if (isset($links[$type])) {
             $links[$type] = $this->jsHelper->decodeGridSerializedInput($links[$type]);
         }
     }
     $product = $this->productLinks->initializeLinks($product, $links);
     $productLinks = $product->getProductLinks();
     $linkTypes = ['related' => $product->getRelatedReadonly(), 'upsell' => $product->getUpsellReadonly(), 'crosssell' => $product->getCrosssellReadonly()];
     foreach ($linkTypes as $linkType => $readonly) {
         if (isset($links[$linkType]) && !$readonly) {
             foreach ($links[$linkType] as $linkId => $linkData) {
                 $linkProduct = $this->productRepository->getById($linkId);
                 $link = $this->productLinkFactory->create();
                 $link->setSku($product->getSku())->setLinkedProductSku($linkProduct->getSku())->setLinkType($linkType)->setPosition(isset($linkData['position']) ? (int) $linkData['position'] : 0);
                 $productLinks[] = $link;
             }
         }
     }
     $product->setProductLinks($productLinks);
     /**
      * Initialize product options
      */
     if (isset($productData['options']) && !$product->getOptionsReadonly()) {
         // mark custom options that should to fall back to default value
         $options = $this->mergeProductOptions($productData['options'], $this->request->getPost('options_use_default'));
         $customOptions = [];
         foreach ($options as $customOptionData) {
             if (!(bool) $customOptionData['is_delete']) {
                 $customOption = $this->customOptionFactory->create(['data' => $customOptionData]);
                 $customOption->setProductSku($product->getSku());
                 $customOption->setOptionId(null);
                 $customOptions[] = $customOption;
             }
         }
         $product->setOptions($customOptions);
     }
     $product->setCanSaveCustomOptions((bool) $this->request->getPost('affect_product_custom_options') && !$product->getOptionsReadonly());
     return $product;
 }