增加库存
@param $productId 商品ID
@param $quantity 增加的库存数量
@param array $skuInfo sku信息,格式"id1:vid1;id2:vid2",如商品为统一规格，则此处赋值为空字符串即可
@return bool
492900
public function addProductStock($productId, $quantity, array $skuInfo = null)
    {
        $result = $this->httpRaw(self::WECHAT_SHOP_PRODUCT_STOCK_ADD_URL . 'access_token=' . $this->getAccessToken(), [
            'product_id' => $productId,
            'quantity' => $quantity,
            'sku_info' => $skuInfo === null ? $skuInfo : implode(':', $skuInfo)
        ]);
        return isset($result['errmsg']) && $result['errmsg'] == 'success';
    }
432963
public function insert($productId, $skuId, LicenseAssignmentInsert $postBody, $optParams = array()) {
      $params = array('productId' => $productId, 'skuId' => $skuId, 'postBody' => $postBody);
      $params = array_merge($params, $optParams);
      $data = $this->__call('insert', array($params));
      if ($this->useObjects()) {
        return new LicenseAssignment($data);
      } else {
        return $data;
      }
    }
579698
public function addProductAction(Product $product, $quantity, Request $request)
    {
        // Find OrderCollection
        $orderCollection = $this->getCurrentCart();

        $quantity = array_key_exists('quantity', $_POST) ? (int) $_POST['quantity'] : $quantity;

        try
        {
            if ('-' == $request->get('remove'))
            {
                $quantity = -1 * $quantity;
            }

            // Add Product to OrderCollection
            $lineItem = $orderCollection->addProduct($product, $quantity);

            // Persisting cascades to Order and OrderCollection
            $em = $this->getDoctrine()->getEntityManager();
            $em->persist($lineItem);
            $em->flush();

            if ($quantity > 0) {
                $notice = 'Added '.$quantity.' '
                    .$product->getUnitForNumber($quantity).' of '
                    .$product->getName().' to your cart';
            } else {
                $quantity = abs($quantity);
                $notice = 'Removed '.$quantity.' '
                    .$product->getUnitForNumber($quantity).' of '
                    .$product->getName().' from your cart';
            }

            // Set flash message
            $this->get('session')->getFlashBag()->add('notice', $notice);

            // Save the OrderCollection to the session
            $this->getRequest()->getSession()->set('cart_id', $orderCollection->getId());
        }
        catch (\Exception $e)
        {
            // could not add Product to cart
        }

        $last_route = $request->get('referer');

        if (in_array($last_route, array('_welcome')))
        {
            return $this->redirect($this->generateUrl($last_route));
        }

        return $this->redirect($this->generateUrl('Profile_product_show', array(
            'product_slug' => $product->getSlug(),
            'slug'         => $product->getSeller()->getSlug(),
        )));
    }
838561
public function setProductID($productID) {
        if (empty($productID))
            throw new Exception('Product ID must be set and cannot be empty.');

        $this->productID = trim($productID);

        return $this;
    }
422651
private function getEffectOnProduct($baseProductIds, $optimizedProductIds, $productId)
    {
        $result                   = 0;
        $baseProductPosition      = array_search($productId, $baseProductIds);
        $optimizedProductPosition = array_search($productId, $optimizedProductIds);

        if ($baseProductPosition === false && $optimizedProductPosition !== false) {
            $result = 1;
        } elseif ($baseProductPosition !== false && $optimizedProductPosition === false) {
            $result = -1;
        } elseif ($baseProductPosition !== false && $optimizedProductPosition !== false) {
            if ($baseProductPosition > $optimizedProductPosition) {
                $result = 1;
            }
            if ($baseProductPosition < $optimizedProductPosition) {
                $result = -1;
            }
        }

        return $result;
    }
855450
protected function prepareProductInformation($addProductId, $productInfo)
    {
        $return = [];

        $return['id'] = isset($productInfo['aid']) ? $productInfo['aid'] : $addProductId;
        $return['amount'] = isset($productInfo['am']) ? $productInfo['am'] : 0;
        $return['selectList'] = isset($productInfo['sel']) ? $productInfo['sel'] : null;

        $return['persistentParameters'] = $this->getPersistedParameters($productInfo['persparam']);
        $return['override'] = isset($productInfo['override']) ? $productInfo['override'] : null;
        $return['bundle'] = isset($productInfo['bundle']) ? true : false;
        $return['oldBasketItemId'] = isset($productInfo['basketitemid']) ? $productInfo['basketitemid'] : null;

        return $return;
    }
696240
public function setQuantity($uniqueId, $quantity)
    {
        if ($cartItem = $this->get($uniqueId)) {
            $cartItem->quantity = $quantity;

            $this->content->put($cartItem->getUniqueId(), $cartItem);

            return true;
        }

        return false;
    }
1080385
public function update($itemId, $quantity)
    {
        if ($cartItem = $this->get($itemId)) {
            $cartItem->canChangeQuantity($quantity);
            $cartItem->quantity = $quantity;
            $cartItem->save();
        }

        return $cartItem;
    }
714860
public function isContainsProduct($productId, $combinationId = null)
    {
        if (Yii::$app->user->isGuest) {
            if (!empty(Yii::$app->session[self::SESSION_KEY])) {
                $sessionProducts = Yii::$app->session[self::SESSION_KEY];

                foreach ($sessionProducts as $item) {
                    $condition = (empty($combinationId))
                        ? (ArrayHelper::getValue($item, 'id') == $productId)
                        : (ArrayHelper::getValue($item, 'id') == $productId && ArrayHelper::getValue($item, 'combinationId') == $combinationId);

                    if($condition) {
                        return $condition;
                    }
                }
            }
        } else {
            /** @var Order $order */
            $order = Order::find()
                ->where(['user_id' => Yii::$app->user->id, 'status' => OrderStatus::STATUS_INCOMPLETE])
                ->one();

            if (!empty($order)) {
                $condition = (empty($combinationId))
                    ? ['order_id' => $order->id, 'product_id' => $productId]
                    : ['order_id' => $order->id, 'product_id' => $productId, 'combination_id' => $combinationId];

                $product = OrderProduct::find()
                    ->where($condition)
                    ->one();

                return (!empty($product));
            }
        }

        return false;
    }
1333296
public function deleteProduct($productId)
    {
        $result = $this->httpRaw(self::WECHAT_SHOP_PRODUCT_DELETE_URL . 'access_token=' . $this->getAccessToken(), [
            'product_id' => $productId
        ]);
        return isset($result['errmsg']) && $result['errmsg'] == 'success';
    }
192668
public function updateProductStatus($productId, $status)
    {
        $result = $this->httpRaw(self::WECHAT_SHOP_STATUS_PRODUCT_UPDATE_URL . 'access_token=' . $this->getAccessToken(), [
                'product_id' => $productId,
                'status' => $status
            ]);
        return isset($result['errmsg']) && $result['errmsg'] == 'success';
    }
1037707
public function updateSku($productId, $sku)
    {
        $skuId = "";

        if (is_array($sku)) {
            $skuId = $sku["id"];
            unset($sku["id"]);
        }
        elseif (is_object($sku)) {
            $skuId = $sku->id;
            unset($sku->id);
        }

        return $this->client->put("/products/" . rawurlencode($productId) . "/skus/" . rawurlencode($skuId), $sku);
    }
44355
public function actionAddAdditional(int $productId, int $languageId)
    {
        $additionalProductsCategories = Category::find()->with('products')
            ->where(['additional_products' => true])->all();

        $productAdditionalProducts = ProductAdditionalProduct::find()->where(['product_id' => $productId])->all();
        return $this->render('../product/save', [
            'viewName' => '../additional-product/add-additional',
            'selectedLanguage' => Language::findOne($languageId),
            'product' => Product::findOne($productId),
            'languages' => Language::find()->all(),

            'params' => [
                'additionalProductsCategories' => $additionalProductsCategories,
                'productAdditionalProducts' => $productAdditionalProducts,
                'productId' => $productId
            ]
        ]);
    }
1026101
public function findByAttributeIdAndProductId($attributeId, $productId)
    {
        try {
            $queryBuilder = $this->createQueryBuilder('productAttribute')
                ->leftJoin('productAttribute.attribute', 'attribute')
                ->leftJoin('productAttribute.product', 'product')
                ->andWhere('attribute.id = :attributeId')
                ->andWhere('product.id = :productId')
                ->setParameter('attributeId', $attributeId)
                ->setParameter('productId', $productId);

            return $queryBuilder->getQuery()->getSingleResult();
        } catch (NoResultException $exc) {
            return null;
        }
    }
271259
protected function buildProductVariation(
        array &$productData,
        $sku,
        $qty,
        $ean,
        array $images = [],
        array $specifications = []
    ) {
        $transformer = new Create($sku, $qty, $ean, $images, $specifications);
        $output      = $transformer->output();

        $productData['variations'][] = $output['variation'];

        return $productData;
    }
147375
private function saveProductToSession(int $productId, int $count, $attributesAndValues = null, $additionalProducts = [], $combinationId = null)
    {
        if (!empty($productId) && (!empty($count))) {

            $additionalProductsArray = [];
            if (!empty($additionalProducts)) {
                foreach ($additionalProducts as $additionalProduct) {
                    $additionalProductsArray[] = [
                        'productId' => $additionalProduct->productId,
                        'number' => $additionalProduct->number
                    ];
                }
            }

            $session = Yii::$app->session;
            $productsFromSession = $session[self::SESSION_KEY];

            if (\Yii::$app->getModule('shop')->enableCombinations) {
                if (!empty($attributesAndValues)) {
                    $combination = $this->getCombination($attributesAndValues, $productId);
                    if (!empty($combination)) $combinationId = $combination->id;
                }
            }

            if (!empty($productsFromSession)) {
                foreach ($productsFromSession as $key => $product) {

                    if ($product['id'] == $productId) {

                        if (\Yii::$app->getModule('shop')->enableCombinations && !empty($combinationId)) {

                            if ($product['combinationId'] == $combinationId) {
                                $productsFromSession[$key]['count'] += $count;

                                $productsFromSession[$key]['additionalProducts'] = (empty($productsFromSession[$key]['additionalProducts'])) ?
                                    $additionalProductsArray : array_merge($productsFromSession[$key]['additionalProducts'], $additionalProductsArray);

                                break;
                            }
                        } else {
                            if (empty($product['combinationId'])) {
                                $productsFromSession[$key]['count'] += $count;
                                $productsFromSession[$key]['additionalProducts'] = (empty($productsFromSession[$key]['additionalProducts'])) ?
                                    $additionalProductsArray : array_merge($productsFromSession[$key]['additionalProducts'], $additionalProductsArray);

                                break;
                            }
                        }
                    }
                    if (count($productsFromSession) - 1 == $key) {
                        $productsFromSession[] =
                            [
                                'id' => $productId,
                                'count' => $count,
                                'combinationId' => $combinationId,
                                'additionalProducts' => $additionalProductsArray
                            ];
                    }
                }
                $session[self::SESSION_KEY] = $productsFromSession;
            } else {
                $_SESSION[self::SESSION_KEY][] =
                    [
                        'id' => $productId,
                        'count' => $count,
                        'combinationId' => $combinationId,
                        'additionalProducts' => $additionalProductsArray
                    ];
            }
            return true;
        }
        return false;
    }
1225019
public function increase( $productCode, $warehouseCode, $amount )
	{
		$context = $this->_getContext();

		$productManager = MShop_Factory::createManager( $context, 'product' );
		$search = $productManager->createSearch();
		$search->setConditions( $search->compare( '==', 'product.code', $productCode ) );
		$productIds = array_keys( $productManager->searchItems( $search ) );

		$warehouseManager = $this->getSubManager( 'warehouse' );
		$search = $warehouseManager->createSearch();
		$search->setConditions( $search->compare( '==', 'product.stock.warehouse.code', $warehouseCode ) );
		$warehouseIds = array_keys( $warehouseManager->searchItems( $search ) );

		if( empty( $warehouseIds ) ) {
			throw new MShop_Product_Exception( sprintf( 'No warehouse for code "%1$s" found', $warehouseCode ) );
		}

		$search = $this->createSearch();
		$expr = array(
			$search->compare( '==', 'product.stock.siteid', $context->getLocale()->getSitePath() ),
			$search->compare( '==', 'product.stock.productid', $productIds ),
			$search->compare( '==', 'product.stock.warehouseid', $warehouseIds ),
		);
		$search->setConditions( $search->combine( '&&', $expr ) );

		$types = array(
			'product.stock.siteid' => $this->_searchConfig['product.stock.siteid']['internaltype'],
			'product.stock.productid' => $this->_searchConfig['product.stock.productid']['internaltype'],
			'product.stock.warehouseid' => $this->_searchConfig['product.stock.warehouseid']['internaltype'],
		);
		$translations = array(
			'product.stock.siteid' => '"siteid"',
			'product.stock.productid' => '"prodid"',
			'product.stock.warehouseid' => '"warehouseid"',
		);

		$conditions = $search->getConditionString( $types, $translations );

		$dbm = $context->getDatabaseManager();
		$dbname = $this->_getResourceName();
		$conn = $dbm->acquire( $dbname );

		try
		{
			/** mshop/product/manager/stock/default/item/stocklevel
			 * Increases or decreases the stock level for the given product and warehouse code
			 *
			 * The stock level is decreased for the ordered products each time
			 * an order is placed by a customer successfully. Also, updates
			 * from external sources like ERP systems can increase the stock
			 * level of a product if no absolute values are set via saveItem()
			 * instead.
			 *
			 * The stock level must be from one of the sites that are configured
			 * via the context item. If the current site is part of a tree of
			 * sites, the statement can increase or decrease stock levels from
			 * the current site and all parent sites if the stock level is
			 * inherited by one of the parent sites.
			 *
			 * Each time the stock level is updated, the modification time is
			 * set to the current timestamp and the editor field is updated.
			 *
			 * @param string SQL statement for increasing/decreasing the stock level
			 * @since 2014.03
			 * @category Developer
			 * @see mshop/product/manager/stock/default/item/insert
			 * @see mshop/product/manager/stock/default/item/update
			 * @see mshop/product/manager/stock/default/item/newid
			 * @see mshop/product/manager/stock/default/item/delete
			 * @see mshop/product/manager/stock/default/item/search
			 * @see mshop/product/manager/stock/default/item/count
			 */
			$path = 'mshop/product/manager/stock/default/item/stocklevel';
			$stmt = $conn->create( str_replace( ':cond', $conditions, $context->getConfig()->get( $path, $path ) ) );

			$stmt->bind( 1, $amount, MW_DB_Statement_Abstract::PARAM_INT );
			$stmt->bind( 2, date( 'Y-m-d H:i:s' ) ); //mtime
			$stmt->bind( 3, $context->getEditor() );

			$stmt->execute()->finish();

			$dbm->release( $conn, $dbname );
		}
		catch( Exception $e )
		{
			$dbm->release( $conn, $dbname );
			throw $e;
		}
	}