searchCriteriaBuilder->addFilter( $this->filterBuilder->setField('product_id')->setValue($orderItem->getProductId())->create() ) ->create(); $result = $this->subItemRepository->getList($criteria); $this->logger->debug(sprintf('$orderItem product sku %s, id:%d contains %d', $orderItem->getSku(), $orderItem->getProductId(), $result->getTotalCount())); foreach ($result->getItems() as $subItem) { $this->logger->debug(sprintf(' %s, id:%d contains', $orderItem->getSku(), $orderItem->getProductId()), $subItem->getData()); $subProduct = $this->productRepository->getById($subItem->getSubProductId()); if (isset($items[$subItem->getSubProductId()])) { $this->subItems[$subItem->getSubProductId()]['qty'] += $orderItem->getQtyOrdered() * intval($subItem->getQuality()); } else { $this->subItems[$subItem->getSubProductId()] = [ 'qty' => $orderItem->getQtyOrdered() * intval($subItem->getQuality()), 'sku' => $subProduct->getSku(), ]; } $this->subProductsParent[$subItem->getSubProductId()] = $orderItem->getSku(); } } /** * @param Order\Item $orderItem * @return void */ protected function getSubItemQtyOrdered(Order\Item $orderItem) { try { $this->getSubItemsFromOrderItem($orderItem); $this->logger->debug('$this->subItems: ', $this->subItems); $sourceItems = []; foreach ($this->subItems as $subItem) { $items = $this->getSourceItemsBySku->execute($subItem['sku']); foreach ($items as $sourceItem) { if ($sourceItem->getSourceCode() === self::DEFAULT_SOURCE_CODE) { $this->logger->debug(sprintf('source item %s, product sku: %s, product stock:%f, qty:%d', $sourceItem->getSourceCode(), $subItem['sku'], $sourceItem->getQuantity(), $subItem['qty'])); $newQty = $sourceItem->getQuantity() - $subItem['qty']; $sourceItem->setQuantity($newQty); $sourceItems[] = $sourceItem; } } } if (!empty($sourceItems)) { $this->sourceItemsSave->execute($sourceItems); } } catch (LocalizedException $e) { $this->logger->critical('subitem getSubItemQtyOrdered error: '.$e->getMessage(), $e->getTrace()); } } /** * @param Order $order * @param array $items * @return void * @throws NoSuchEntityException * @throws \Magento\Framework\Exception\CouldNotSaveException * @throws \Magento\Framework\Exception\InputException * @throws \Magento\Framework\Validation\ValidationException */ protected function appendReservations(Order $order, array $items) { $stockId = $this->getAssignedStockIdForWebsite->execute($order->getStore()->getWebsite()->getCode()); $reservations = []; foreach ($items as $subProductId => $item) { $reservations[] = $this->reservationBuilder->setSku($item['sku']) ->setQuantity(-$item['qty']) ->setStockId($stockId) ->setMetadata( json_encode([ 'event_type'=>SalesEventInterface::EVENT_ORDER_PLACED, 'object_type'=>SalesEventInterface::OBJECT_TYPE_ORDER, 'object_id'=>$order->getId(), 'object_increment_id' => $order->getIncrementId(), 'comment' => 'sub product of '.$this->subProductsParent[$subProductId], ]) ) ->build(); } $this->appendReservations->execute($reservations); } public function execute(Observer $observer) { /* @var $order Order */ $order = $observer->getData('order'); /* @var $item Order\Item */ foreach ($order->getAllVisibleItems() as $item) { $qty = (int)$item->getQtyOrdered(); try { $product = $this->productRepository->get($item->getSku()); $this->subItemResourceModel->getConnection()->query(" update subitem_product set stock_qty = stock_qty - (bundle_qty*$qty) where product_id={$product->getEntityId()}; "); } catch (NoSuchEntityException $e) { } } } }