23 if ($fuserId ===
null)
33 if (!empty($_SESSION[
'SALE_USER_BASKET_QUANTITY'][$siteId]) && is_array($_SESSION[
'SALE_USER_BASKET_QUANTITY'][$siteId])
34 && array_key_exists($fuserId, $_SESSION[
'SALE_USER_BASKET_QUANTITY'][$siteId]))
36 $quantity = $_SESSION[
'SALE_USER_BASKET_QUANTITY'][$siteId][$fuserId];
39 if ($quantity ===
null)
41 static::updateFUserBasketQuantity($fuserId, $siteId);
42 $quantity = $_SESSION[
'SALE_USER_BASKET_QUANTITY'][$siteId][$fuserId];
56 if ($fuserId ===
null)
66 if (!empty($_SESSION[
'SALE_USER_BASKET_PRICE'][$siteId]) && is_array($_SESSION[
'SALE_USER_BASKET_PRICE'][$siteId])
67 && array_key_exists($fuserId, $_SESSION[
'SALE_USER_BASKET_PRICE'][$siteId]))
69 $price = $_SESSION[
'SALE_USER_BASKET_PRICE'][$siteId][$fuserId];
74 static::updateFUserBasketPrice($fuserId, $siteId);
75 $price = $_SESSION[
'SALE_USER_BASKET_PRICE'][$siteId][$fuserId];
94 $_SESSION[
'SALE_USER_BASKET_QUANTITY'][$siteId][$fUserId] = $quantity;
103 if ($siteId ===
null)
108 unset($_SESSION[
'SALE_USER_BASKET_QUANTITY'][$siteId][$fUserId]);
119 if ($siteId ===
null)
124 $_SESSION[
'SALE_USER_BASKET_PRICE'][$siteId][$fUserId] = $price;
133 if ($siteId ===
null)
138 unset($_SESSION[
'SALE_USER_BASKET_PRICE'][$siteId][$fUserId]);
150 if ($siteId ===
null)
157 if ($basketList ===
null)
159 $basketList = static::getFUserBasketList($fuserId, $siteId);
162 if (!empty($basketList) && is_array($basketList))
164 $orderData = static::calculatePrice($fuserId, $basketList);
165 $price = $orderData[
'ORDER_PRICE'];
168 static::setFUserBasketPrice($fuserId, $price, $siteId);
180 if ($siteId ===
null)
187 if ($basketList ===
null)
189 $basketList = static::getFUserBasketList($fuserId, $siteId);
192 if (!empty($basketList) && is_array($basketList))
194 $quantity = count($basketList);
197 static::setFUserBasketQuantity($fuserId, $quantity, $siteId);
208 if ($siteId ===
null)
213 $basketList = static::getFUserBasketList($fuserId, $siteId);
215 static::updateFUserBasketPrice($fuserId, $siteId, $basketList);
216 static::updateFUserBasketQuantity($fuserId, $siteId, $basketList);
225 protected static function getFUserBasketList($fuserId, $siteId =
null)
227 if ($siteId ===
null)
234 $basketClassName = $registry->getBasketClassName();
236 $basketList = array();
237 $res = $basketClassName::getList(array(
239 '=FUSER_ID' => $fuserId,
246 while ($data = $res->fetch())
248 if (\CSaleBasketHelper::isSetItem($data))
251 if (!isset($data[
'BASE_PRICE']) || (
float)$data[
'BASE_PRICE'] <= 0)
253 $data[
'BASE_PRICE'] = $data[
'PRICE'] + $data[
'DISCOUNT_PRICE'];
256 $basketList[] = $data;
268 protected static function calculatePrice($fuserId, array $basketList)
273 foreach ($basketList as $basketData)
275 $totalPrice += $basketData[
"PRICE"] * $basketData[
"QUANTITY"];
276 $totalWeight += $basketData[
"WEIGHT"] * $basketData[
"QUANTITY"];
280 'SITE_ID' => SITE_ID,
281 'ORDER_PRICE' => $totalPrice,
282 'ORDER_WEIGHT' => $totalWeight,
283 'BASKET_ITEMS' => $basketList
288 $basketClassName = $registry->getBasketClassName();
290 $basket = $basketClassName::create(SITE_ID);
291 $basket->setFUserId($fuserId);
292 foreach ($basketList as $oldItem)
294 $item = $basket->createItem($oldItem[
'MODULE'], $oldItem[
'PRODUCT_ID']);
295 unset($oldItem[
'MODULE'], $oldItem[
'PRODUCT_ID']);
296 $item->initFields($oldItem);
298 $orderData[
'ORDER_PRICE'] = self::calculateBasketCost($basket);
310 public static function onSaleBasketItemEntitySaved(Main\Event $event)
313 $basketItem = $event->getParameter(
'ENTITY');
315 $originalValues = $event->getParameter(
'VALUES');
316 if ((!$basketItem instanceof BasketItem))
318 return new Main\EventResult( Main\EventResult::SUCCESS,
null,
'sale');
322 if ((!$basket = $basketItem->getCollection())
323 || ($basketItem->getFUserId() != $fuserId)
326 return new Main\EventResult( Main\EventResult::SUCCESS,
null,
'sale');
329 if ($basketItem->isChanged())
331 $updateSessionData =
false;
333 if (!$basket->getOrder())
335 if (!$updateSessionData && array_key_exists(
'QUANTITY', $originalValues))
337 $updateSessionData =
true;
342 $updateSessionData =
true;
347 $updateSessionData =
true;
351 if (!$updateSessionData && (array_key_exists(
'ORDER_ID', $originalValues) && (intval($originalValues[
'ORDER_ID'])) == 0 && intval($basketItem->getField(
'ORDER_ID') > 0)))
353 $updateSessionData =
true;
356 if (!$updateSessionData
357 && (array_key_exists(
'CAN_BUY', $originalValues) && ($originalValues[
'CAN_BUY'] !== $basketItem->getField(
'CAN_BUY'))))
359 $updateSessionData =
true;
362 if (!$updateSessionData
363 && (array_key_exists(
'DELAY', $originalValues) && ($originalValues[
'DELAY'] !== $basketItem->getField(
'DELAY'))))
365 $updateSessionData =
true;
368 if ($updateSessionData)
370 static::clearFUserBasketPrice($fuserId, SITE_ID);
371 static::clearFUserBasketQuantity($fuserId, SITE_ID);
375 return new Main\EventResult( Main\EventResult::SUCCESS,
null,
'sale');
386 $originalValues = $event->getParameter(
'VALUES');
387 if ($originalValues[
'FUSER_ID'] != $fuserId)
392 static::clearFUserBasketPrice($fuserId, SITE_ID);
393 static::clearFUserBasketQuantity($fuserId, SITE_ID);
405 public static function checkQuantityRatio(
Basket $basket,
BasketItem $item =
null)
409 $basketItemRatioList = array();
410 $ratioList = array();
411 $ratioResult = static::getRatio($basket, $item);
413 if ($ratioResult->isSuccess())
415 $ratioData = $ratioResult->getData();
417 if (!empty($ratioData[
'RATIO_LIST']) && is_array($ratioData[
'RATIO_LIST']))
419 $ratioList = $ratioData[
'RATIO_LIST'];
424 foreach ($basket as $basketItem)
426 $basketItemCode = $basketItem->getBasketCode();
428 if ($item ===
null || $item->getBasketCode() === $basketItemCode)
430 $basketItemRatioList[$basketItemCode] =
false;
432 if (isset($ratioList[$basketItemCode]))
434 $basketItemQuantity = $basketItem->getQuantity();
435 $basketItemRatio = (float)$ratioList[$basketItemCode];
437 $mod = roundEx(($basketItemQuantity / $basketItemRatio - round($basketItemQuantity / $basketItemRatio)), 6);
441 $basketItemRatioList[$basketItemCode] =
true;
447 if (!empty($basketItemRatioList))
449 $result->addData(array(
'CHECK_RATIO_LIST' => $basketItemRatioList));
464 public static function correctQuantityRatio(Basket $basket, BasketItem $item =
null)
466 $result =
new Result();
467 $changedItems = array();
469 $checkRatioList = array();
470 $checkRatioResult = static::checkQuantityRatio($basket, $item);
472 if ($checkRatioResult->isSuccess())
474 $checkRatioData = $checkRatioResult->getData();
476 if (!empty($checkRatioData[
'CHECK_RATIO_LIST']) && is_array($checkRatioData[
'CHECK_RATIO_LIST']))
478 $checkRatioList = $checkRatioData[
'CHECK_RATIO_LIST'];
482 $basketItemRatioList = array();
486 foreach ($basket as $basketItem)
488 $basketItemCode = $basketItem->getBasketCode();
490 if ($item ===
null || $item->getBasketCode() === $basketItemCode)
492 $basketItemRatioList[$basketItemCode] =
false;
494 if (isset($checkRatioList[$basketItemCode]) && $checkRatioList[$basketItemCode] ===
false)
496 if ($ratioList ===
null)
498 $ratioList = array();
499 $ratioResult = static::getRatio($basket, $item);
501 if ($ratioResult->isSuccess())
503 $ratioData = $ratioResult->getData();
505 if (!empty($ratioData[
'RATIO_LIST']) && is_array($ratioData[
'RATIO_LIST']))
507 $ratioList = $ratioData[
'RATIO_LIST'];
512 if (!isset($ratioList[$basketItemCode]))
514 $result->addError(
new ResultError(Main\Localization\
Loc::getMessage(
'SALE_BASKET_COMPONENT_HELPER_PRODUCT_RATIO_NOT_FOUND', array(
515 '#PRODUCT_NAME#' => $basketItem->getField(
'NAME')
516 )),
'SALE_BASKET_COMPONENT_HELPER_PRODUCT_RATIO_NOT_FOUND'));
520 $basketItemQuantity = $basketItem->getQuantity();
521 $basketItemRatio = (float)$ratioList[$basketItemCode];
523 $mod = roundEx(($basketItemQuantity / $basketItemRatio - round($basketItemQuantity / $basketItemRatio)), 6);
527 $changedItems[] = $basketItemCode;
529 $closestQuantity = round($basketItemQuantity / $basketItemRatio) * $basketItemRatio;
530 if ($closestQuantity < $basketItemRatio)
532 $closestQuantity = $basketItemRatio;
535 $r = $basketItem->setField(
'QUANTITY', $closestQuantity);
536 if (!$r->isSuccess())
538 $floorQuantity = floor(ceil($basketItemQuantity) / $basketItemRatio) * $basketItemRatio;
539 if ($floorQuantity < $basketItemRatio)
541 $floorQuantity = $basketItemRatio;
544 if ($floorQuantity != $closestQuantity)
546 $r = $basketItem->setField(
'QUANTITY', $floorQuantity);
550 if (!$r->isSuccess())
552 $result->addErrors($r->getErrors());
554 $r = $basketItem->setField(
'CAN_BUY',
'N');
555 if (!$r->isSuccess())
557 $result->addErrors($r->getErrors());
565 $result->addData(array(
'CHANGED_BASKET_ITEMS' => $changedItems));
577 public static function getRatio(Basket $basket, BasketItem $item =
null)
579 $result =
new Result();
580 $ratioList = array();
581 if (Main\Loader::includeModule(
'catalog'))
584 $elementList = array();
587 foreach ($basket as $basketItem)
589 $code = $basketItem->getBasketCode();
590 if ($item !==
null && $item->getBasketCode() != $code)
595 $hash = md5((strval($basketItem->getField(
"PRODUCT_PROVIDER_CLASS")) !=
'' ? $basketItem->getField(
"PRODUCT_PROVIDER_CLASS"):
"").
"|".(strval($basketItem->getField(
"MODULE")) !=
'' ? $basketItem->getField(
"MODULE"):
"").
"|".$basketItem->getField(
"PRODUCT_ID"));
597 if (array_key_exists($hash, static::$cacheRatio))
599 $ratioList[$code] = static::$cacheRatio[$hash];
603 $elementList[$basketItem->getField(
"PRODUCT_ID")] = $basketItem->getField(
"PRODUCT_ID");
606 if (!isset($map[$basketItem->getField(
"PRODUCT_ID")]))
608 $map[$basketItem->getField(
"PRODUCT_ID")] = array();
611 $map[$basketItem->getField(
"PRODUCT_ID")][] = $code;
614 if (!empty($elementList))
616 $res = Catalog\MeasureRatioTable::getList(array(
617 'select' => array(
'*'),
618 'filter' => array(
'@PRODUCT_ID' => $elementList,
'=IS_DEFAULT' =>
'Y')
620 while ($ratioData = $res->fetch())
622 if (empty($map[$ratioData[
"PRODUCT_ID"]]))
625 foreach ($map[$ratioData[
"PRODUCT_ID"]] as $key)
627 $ratioList[$key] = $ratioData[
"RATIO"];
629 if (!$basketItem = $basket->getItemByBasketCode($key))
632 $hash = md5((strval($basketItem->getField(
"PRODUCT_PROVIDER_CLASS")) !=
'' ? $basketItem->getField(
"PRODUCT_PROVIDER_CLASS"):
"").
"|".(strval($basketItem->getField(
"MODULE")) !=
'' ? $basketItem->getField(
"MODULE"):
"").
"|".$basketItem->getField(
"PRODUCT_ID"));
634 static::$cacheRatio[$hash] = $ratioData[
"RATIO"];
635 static::$cacheRatioData[$hash] = $ratioData;
639 unset($ratioData, $dbRatio);
641 unset($elementList, $map);
644 if (!empty($ratioList))
645 $result->addData(array(
'RATIO_LIST' => $ratioList));
655 protected static function calculateBasketCost(Basket $basket)
657 if ($basket->count() == 0)
660 $oldApiStatus = Compatible\DiscountCompatibility::isUsed();
662 Compatible\DiscountCompatibility::stopUsageCompatible();
664 $basket->refreshData(array(
'PRICE',
'COUPONS'));
665 $discounts = Discount::buildFromBasket($basket,
new Discount\Context\Fuser($basket->getFUserId(
true)));
666 $discounts->calculate();
667 $discountResult = $discounts->getApplyResult();
670 Compatible\DiscountCompatibility::revertUsageCompatible();
672 if (empty($discountResult[
'PRICES'][
'BASKET']))
676 $discountResult = $discountResult[
'PRICES'][
'BASKET'];
678 foreach ($basket as $basketItem)
680 if (!$basketItem->canBuy())
682 $code = $basketItem->getBasketCode();
683 if (!empty($discountResult[$code]))
684 $result += $discountResult[$code][
'PRICE'] * $basketItem->getQuantity();
688 unset($discountResult);
699 return static::$cacheRatio;
708 return static::$cacheRatioData;