Один и тот же товар в корзине новой строкой

#
Один и тот же товар в корзине новой строкой
Здравствуйте.
Подскажите пожалуйста как сделать так чтобы один и тот же товар который попадает в корзину отображался новой строкой, а не прибавлял в количестве +1?
Понимаю, что нужно использовать свой контроллер добавления в корзину, но дальше как-то не продвинулся.
Модератор
#
Re: Один и тот же товар в корзине новой строкой
Вам же в поддержке 7 числа на этот вопрос отвечали:
Цитата:
Только использовать свой контроллер добавления в корзину, тк стандартный при наличии товара изменит его количество.

Цитата:
Использовать унаследованный класс можно в корзине, а сам контроллер можете разместить там же.
#
Re: Один и тот же товар в корзине новой строкой
В поддержке ответили одной строкой о том, что нужно использовать свой контроллер, это и так понятно.
Мне дальше не совсем понятно, пример бы на что-то подобное.
Модератор
#
Re: Один и тот же товар в корзине новой строкой
zdweb,
в методе update() контроллера Shop_Cart_Controller необходимо переписать секцию, начинающуюся с if ($this->quantity > 0)
В случае хранения корзины в базе (для авторизованных клиентов) убрать получение через getByShopItemIdAndSiteuserId и всегда создавать новую запись.
Для хранения в сессии вместо $_SESSION['hostcmsCart'][$oShop_Item->shop_id][$this->shop_item_id] использовать $_SESSION['hostcmsCart'][$oShop_Item->shop_id][] и в сам массив добавить
'shop_item_id' => $this->shop_item_id,
                  $_SESSION['hostcmsCart'][$oShop_Item->shop_id][] = array(
                     'shop_item_id' => $this->shop_item_id,
                     'quantity' => $this->quantity,
                     'postpone' => $this->postpone,
                     'marking' => $this->marking,
                     'siteuser_id' => $this->siteuser_id,
                     'shop_warehouse_id' => $this->shop_warehouse_id
                  );

также потребуется модифицировать _getAllFromSession, код
foreach ($aCart[$shop_id] as $shop_item_id => $aCartItem)
      {

заменяется на
foreach ($aCart[$shop_id] as $shop_item_id => $aCartItem)
      {
         if (isset($aCartItem['shop_item_id']))
         {
            $shop_item_id = $aCartItem['shop_item_id'];
         }
#
Re: Один и тот же товар в корзине новой строкой
Спасибо вам огромное.
Сам бы точно не разобрался.
Все работает за исключением того когда обновляешь страничку после добавления товара в корзину, уходит в 502 ошибку.
Я так понимаю дело в этом коде:

      if ($this->siteuser_id)
      {
         $oShop_Cart = Core_Entity::factory('Shop_Cart')
            ->getByShopItemIdAndSiteuserId($this->shop_item_id, $this->siteuser_id, FALSE);

         if (is_null($oShop_Cart))
         {
            $oShop_Cart = Core_Entity::factory('Shop_Cart');
            $oShop_Cart->shop_item_id = $this->shop_item_id;
            $oShop_Cart->siteuser_id = $this->siteuser_id;
         }
      }


я переписал его на

         Core_Session::start();

         $Shop_Item = Core_Entity::factory('Shop_Item', $this->shop_item_id);

         $aCart = Core_Array::getSession('hostcmsCart', array());
         $aCart[$Shop_Item->shop_id] = Core_Array::get($aCart, $Shop_Item->shop_id, array());

         $aReturn = Core_Array::get($aCart[$Shop_Item->shop_id], $this->shop_item_id, array()) + array(
            'shop_item_id' => $this->shop_item_id,
            'quantity' => 0,
            'postpone' => 0,
            'marking' => '',
            'shop_id' => $Shop_Item->shop_id,
            'shop_warehouse_id' => 0
         );

         $oShop_Cart = (object)$aReturn;


но не помогло.
Модератор
#
Re: Один и тот же товар в корзине новой строкой
первый код должен быть заменен на
  if ($this->siteuser_id)
      {
            $oShop_Cart = Core_Entity::factory('Shop_Cart');
            $oShop_Cart->shop_item_id = $this->shop_item_id;
            $oShop_Cart->siteuser_id = $this->siteuser_id;
      }
, остальные изменения по пунктам из предыдущего ответа.
#
Re: Один и тот же товар в корзине новой строкой
К сожалению, не помогло.
При обновлении страницы после добавления товаров уходит в 502 ошибку.
Модератор
#
Re: Один и тот же товар в корзине новой строкой
zdweb,
у меня работает, проверка на версии 6.8.6 и 6.8.7
class My_Shop_Cart_Controller extends Shop_Cart_Controller
{
   /**
    * Get all carts from session
    * @param Shop_Model $oShop shop
    * @return array
    */
   protected function _getAllFromSession(Shop_Model $oShop)
   {
      Core_Session::start();

      $shop_id = $oShop->id;

      $aCart = Core_Array::getSession('hostcmsCart', array());
      $aCart[$shop_id] = Core_Array::get($aCart, $shop_id, array());

      $aShop_Cart = array();
      foreach ($aCart[$shop_id] as $shop_item_id => $aCartItem)
      {
         // Добавлено
         if (isset($aCartItem['shop_item_id']))
         {
            $shop_item_id = $aCartItem['shop_item_id'];
         }
            
         $aCartItem += array(
            'quantity' => 0,
            'postpone' => 0,
            'marking' => '',
            'shop_warehouse_id' => 0
         );

         $oShop_Item = Core_Entity::factory('Shop_Item')->find($shop_item_id);

         if (!is_null($oShop_Item->id) && $oShop_Item->active)
         {
            // Temporary object
            $oShop_Cart = Core_Entity::factory('Shop_Cart');
            $oShop_Cart->shop_item_id = $shop_item_id;
            $oShop_Cart->quantity = $aCartItem['quantity'];
            $oShop_Cart->postpone = $aCartItem['postpone'];
            $oShop_Cart->marking = $aCartItem['marking'];
            $oShop_Cart->shop_id = $shop_id;
            $oShop_Cart->shop_warehouse_id = $aCartItem['shop_warehouse_id'];
            $oShop_Cart->siteuser_id = 0;
            $aShop_Cart[] = $oShop_Cart;
         }
      }

      return $aShop_Cart;
   }

   /**
    * Get item from cart
    * @return object
    * @hostcms-event Shop_Cart_Controller.onBeforeGet
    * @hostcms-event Shop_Cart_Controller.onAfterGet
    */
   public function get()
   {
      Core_Event::notify(get_class($this) . '.onBeforeGet', $this);

      // Проверяем наличие данных о пользователе
      if ($this->siteuser_id)
      {
         $oShop_Cart = Core_Entity::factory('Shop_Cart');
         $oShop_Cart->shop_item_id = $this->shop_item_id;
         $oShop_Cart->siteuser_id = $this->siteuser_id;
      }
      else
      {
         Core_Session::start();

         $Shop_Item = Core_Entity::factory('Shop_Item', $this->shop_item_id);

         $aReturn = array(
            'shop_item_id' => $this->shop_item_id,
            'quantity' => 0,
            'postpone' => 0,
            'marking' => '',
            'shop_id' => $Shop_Item->shop_id,
            'shop_warehouse_id' => 0
         );

         $oShop_Cart = (object)$aReturn;
      }

      Core_Event::notify(get_class($this) . '.onAfterGet', $this);

      return $oShop_Cart;
   }

   /**
    * Delete item from cart
    * @return Shop_Cart_Controller
    * @hostcms-event Shop_Cart_Controller.onBeforeDelete
    * @hostcms-event Shop_Cart_Controller.onAfterDelete
    */
   public function delete()
   {
      Core_Event::notify(get_class($this) . '.onBeforeDelete', $this);

      // Проверяем наличие данных о пользователе
      if ($this->siteuser_id)
      {
         $oShop_Cart = Core_Entity::factory('Shop_Cart')
            ->getByShopItemIdAndSiteuserId($this->shop_item_id, $this->siteuser_id, FALSE);

         !is_null($oShop_Cart) && $oShop_Cart->delete();
      }
      else
      {
         Core_Session::start();
         $oShop_Item = Core_Entity::factory('Shop_Item')->find($this->shop_item_id);
         if (isset($_SESSION['hostcmsCart'][$oShop_Item->shop_id]))
         {
            foreach ($_SESSION['hostcmsCart'][$oShop_Item->shop_id] as $key => $aTmp)
            {
               if (isset($aTmp['shop_item_id']) && $aTmp['shop_item_id'] == $this->shop_item_id)
               {
                  unset($_SESSION['hostcmsCart'][$oShop_Item->shop_id][$key]);
               }
            }
         }
      }

      Core_Event::notify(get_class($this) . '.onAfterDelete', $this);

      return $this;
   }

   /**
    * Update item in cart
    * @return Shop_Cart_Controller
    * @hostcms-event Shop_Cart_Controller.onBeforeUpdate
    * @hostcms-event Shop_Cart_Controller.onAfterUpdate
    */
   public function update()
   {
      $this->_error = FALSE;

      Core_Event::notify(get_class($this) . '.onBeforeUpdate', $this);

      $oShop_Item = Core_Entity::factory('Shop_Item')->find($this->shop_item_id);

      if (!is_null($oShop_Item->id))
      {
         $aSiteuserGroups = array(0, -1);
         if (Core::moduleIsActive('siteuser'))
         {
            $oSiteuser = Core_Entity::factory('Siteuser', $this->siteuser_id);

            if ($oSiteuser)
            {
               $aSiteuser_Groups = $oSiteuser->Siteuser_Groups->findAll();
               foreach ($aSiteuser_Groups as $oSiteuser_Group)
               {
                  $aSiteuserGroups[] = $oSiteuser_Group->id;
               }
            }
         }

         // Проверяем право пользователя добавить этот товар в корзину
         if (in_array($oShop_Item->getSiteuserGroupId(), $aSiteuserGroups))
         {
            // 1. Check STEP. DECIMAL, > 0, NOT $oShop_Item->quantity_step
            if ($oShop_Item->quantity_step > 0)
            {
               $iStep = $this->quantity / $oShop_Item->quantity_step;

               if (!is_int($iStep))
               {
                  $this->quantity = ceil($iStep) * $oShop_Item->quantity_step;
               }
            }

            // 2. Check MIN quantity
            if ($this->quantity < $oShop_Item->min_quantity)
            {
               $this->quantity = $oShop_Item->min_quantity;
            }

            // 3. Check MAX quantity (DECIMAL, $oShop_Item->max_quantity > 0, NOT $oShop_Item->max_quantity)
            if ($oShop_Item->max_quantity > 0 && $this->quantity > $oShop_Item->max_quantity)
            {
               $this->quantity = $oShop_Item->max_quantity;
            }

            // Нужно получить реальное количество товара, если товар электронный
            if ($oShop_Item->type == 1)
            {
               // Получаем количество электронного товара на складе
               $iShop_Item_Digitals = $oShop_Item->Shop_Item_Digitals->getCountDigitalItems();

               if ($iShop_Item_Digitals != -1 && $iShop_Item_Digitals < $this->quantity)
               {
                  $this->quantity = $iShop_Item_Digitals;
               }
            }

            // Если делимый товар
            if ($oShop_Item->type == 2)
            {
               // Товар делимый, поэтому floatval()
               $this->quantity = floatval($this->quantity);
            }
            else
            {
               // Товар обычный, поэтому intval()
               $this->quantity = intval($this->quantity);
            }

            // Проверять остаток для обычных товаров
            if ($this->checkStock && $oShop_Item->type != 1)
            {
               $iRest = $oShop_Item->getRest() - $oShop_Item->getReserved();
               $iRest < $this->quantity && $this->quantity = $iRest;
            }

            if ($this->quantity > 0)
            {
               // Проверяем наличие данных о пользователе
               if ($this->siteuser_id)
               {
                  $oShop_Cart = Core_Entity::factory('Shop_Cart');
                  $oShop_Cart->shop_item_id = $this->shop_item_id;
                  $oShop_Cart->siteuser_id = $this->siteuser_id;

                  // Вставляем данные в таблицу корзины
                  $oShop_Cart->quantity = $this->quantity;
                  $oShop_Cart->postpone = $this->postpone;
                  strlen($this->marking) && $oShop_Cart->marking = $this->marking;
                  $oShop_Cart->shop_id = $oShop_Item->shop_id;
                  $oShop_Cart->shop_warehouse_id = $this->shop_warehouse_id;
                  $oShop_Cart->save();
               }
               else
               {
                  Core_Session::start();
                  $_SESSION['hostcmsCart'][$oShop_Item->shop_id][] = array(
                     'shop_item_id' => $this->shop_item_id,
                     'quantity' => $this->quantity,
                     'postpone' => $this->postpone,
                     'marking' => $this->marking,
                     'siteuser_id' => $this->siteuser_id,
                     'shop_warehouse_id' => $this->shop_warehouse_id
                  );
               }
            }
            else
            {
               $this->_error = 4;
               $this->delete();
            }
         }
         else
         {
            $this->_error = 3;
         }
      }
      else
      {
         $this->_error = 2;
      }

      Core_Event::notify(get_class($this) . '.onAfterUpdate', $this);

      return $this;
   }
}
#
Re: Один и тот же товар в корзине новой строкой
Разобрался, слишком большая xml формировалась, сервер выдавал ошибку из за долгого выполнения.
Остался последний момент, перестало работать удаление товара и в краткой и в обычной корзине.

Удаление делаю так:
      removeFromCart: function(path, shop_item_id, items){
         $.clientRequest({path: path + '?delete=' + shop_item_id + '&dcompl=' + items, 'callBack': ''});
         location.reload();
         return false;
      },


if (Core_Array::getGet('delete'))
{
   $shop_item_id = intval(Core_Array::getGet('delete'));
  $compl_array = Core_Array::getRequest('dcompl');

  if ($shop_item_id)
   {
      $oShop_Cart_Controller = Shop_Cart_Controller::instance();
      $oShop_Cart_Controller
         ->shop_item_id($shop_item_id)
         ->delete();

      if ($compl_array)
            {

               $compl_array=explode(',',$compl_array);
                foreach($compl_array as $item)
                {
                  $oShop_Cart_Controller
                  ->shop_item_id($item)
                  ->delete();
                }
            }


   }
}
Модератор
#
Re: Один и тот же товар в корзине новой строкой
zdweb,
в приведенном мной коде удаление должно работать корректно
Авторизация