protected Order retrieveCartOrder(HttpServletRequest request, ModelMap model) {
    Customer currentCustomer = customerState.getCustomer(request);
    Order currentCartOrder = null;
    if (currentCustomer != null) {
      currentCartOrder = cartService.findCartForCustomer(currentCustomer);
      if (currentCartOrder == null) {
        currentCartOrder = cartService.createNewCartForCustomer(currentCustomer);
      }
    }

    model.addAttribute("currentCartOrder", currentCartOrder);
    return currentCartOrder;
  }
 protected Order updateFulfillmentGroups(CartSummary cartSummary, Order currentCartOrder)
     throws PricingException {
   FulfillmentGroup fg = cartSummary.getFulfillmentGroup();
   if (fg.getId() == null) {
     cartService.removeAllFulfillmentGroupsFromOrder(currentCartOrder, false);
     for (CartOrderItem item : cartSummary.getRows()) {
       item.getOrderItem().setOrder(currentCartOrder);
       fg =
           cartService.addItemToFulfillmentGroup(
               item.getOrderItem(), fg, item.getQuantity(), false);
     }
     cartSummary.setFulfillmentGroup(fg);
   }
   return cartService.save(currentCartOrder, true);
 }
 @RequestMapping(
     value = "/viewCart.htm",
     params = "updateItemQuantity",
     method = RequestMethod.POST)
 public String updateItemQuantity(
     @ModelAttribute(value = "cartSummary") CartSummary cartSummary,
     Errors errors,
     ModelMap model,
     HttpServletRequest request)
     throws PricingException {
   if (errors.hasErrors()) {
     model.addAttribute("cartSummary", cartSummary);
     return cartView;
   }
   Order currentCartOrder = retrieveCartOrder(request, model);
   List<OrderItem> orderItems = currentCartOrder.getOrderItems();
   List<CartOrderItem> items = new ArrayList<CartOrderItem>(cartSummary.getRows());
   for (CartOrderItem cartOrderItem : items) {
     OrderItem orderItem =
         (OrderItem)
             CollectionUtils.find(
                 orderItems,
                 new BeanPropertyValueEqualsPredicate("id", cartOrderItem.getOrderItem().getId()));
     // in case the item was removed from the cart from another browser tab
     if (orderItem != null) {
       if (cartOrderItem.getQuantity() > 0) {
         orderItem.setQuantity(cartOrderItem.getQuantity());
         try {
           cartService.updateItemQuantity(currentCartOrder, orderItem);
         } catch (ItemNotFoundException e) {
           LOG.error("Item not found in order: (" + orderItem.getId() + ")", e);
         } catch (PricingException e) {
           LOG.error("Unable to price the order: (" + currentCartOrder.getId() + ")", e);
         }
       } else {
         try {
           cartService.removeItemFromOrder(currentCartOrder, orderItem);
           cartSummary.getRows().remove(cartOrderItem);
         } catch (Exception e) {
           // TODO: handle exception gracefully
           LOG.error("Unable to remove item from the order: (" + currentCartOrder.getId() + ")");
         }
       }
     }
   }
   cartSummary.setOrderDiscounts(currentCartOrder.getTotalAdjustmentsValue().getAmount());
   return cartView;
 }
  private String showCatalog(ModelMap model, HttpServletRequest request, CatalogSort catalogSort) {
    addCategoryToModel(request, model);
    boolean productFound = addProductsToModel(request, model, catalogSort);

    String view = defaultCategoryView;
    if (productFound) {
      // TODO: Nice to have: product logic similar to category below
      view = defaultProductView;
    } else {
      Category currentCategory = (Category) model.get("currentCategory");
      if (currentCategory.getUrl() != null && !"".equals(currentCategory.getUrl())) {
        return "redirect:" + currentCategory.getUrl();
      } else if (currentCategory.getDisplayTemplate() != null
          && !"".equals(currentCategory.getUrl())) {
        view = categoryTemplatePrefix + currentCategory.getDisplayTemplate();
      } else {
        if ("true".equals(request.getParameter("ajax"))) {
          view = "catalog/categoryView/mainContentFragment";
        } else {
          view = defaultCategoryView;
        }
      }
    }

    if (catalogSort == null) {
      model.addAttribute("catalogSort", new CatalogSort());
    }

    List<Order> wishlists =
        cartService.findOrdersForCustomer(customerState.getCustomer(request), OrderStatus.NAMED);
    model.addAttribute("wishlists", wishlists);

    return view;
  }
  @RequestMapping(value = "/viewCart.htm", params = "addPromo", method = RequestMethod.POST)
  public String addPromoCode(
      @ModelAttribute(value = "cartSummary") CartSummary cartSummary,
      ModelMap model,
      HttpServletRequest request)
      throws PricingException {
    Order currentCartOrder = retrieveCartOrder(request, model);

    if (cartSummary.getPromoCode() != null) {
      OfferCode code = offerService.lookupOfferCodeByCode(cartSummary.getPromoCode());

      if (code != null) {
        try {
          currentCartOrder = cartService.addOfferCode(currentCartOrder, code, true);
        } catch (OfferMaxUseExceededException e) {
          model.addAttribute("error", "Promotion Max Uses Exceeded");
        }
        currentCartOrder = updateFulfillmentGroups(cartSummary, currentCartOrder);
      } else {
        model.addAttribute("promoError", "Invalid promo code entered.");
      }
    }

    cartSummary.setPromoCode(null);
    model.addAttribute("currentCartOrder", currentCartOrder);
    model.addAttribute("cartSummary", cartSummary);
    return cartView;
  }
  @RequestMapping(
      value = "/viewCart.htm",
      params = "removeItemFromCart",
      method = {RequestMethod.GET, RequestMethod.POST})
  public String removeItem(
      @RequestParam long orderItemId,
      @ModelAttribute CartSummary cartSummary,
      ModelMap model,
      HttpServletRequest request) {
    Order currentCartOrder = retrieveCartOrder(request, model);
    try {
      currentCartOrder = cartService.removeItemFromOrder(currentCartOrder.getId(), orderItemId);
    } catch (PricingException e) {
      model.addAttribute("error", "remove");
      LOG.error("An error occurred while removing an item from the cart: (" + orderItemId + ")", e);
    }
    cartSummary.setOrderDiscounts(currentCartOrder.getTotalAdjustmentsValue().getAmount());

    return removeItemViewRedirect ? "redirect:" + removeItemView : removeItemView;
  }
  @RequestMapping(
      value = "/viewCart.htm",
      params = "removePromoFromCart",
      method = {RequestMethod.GET, RequestMethod.POST})
  public String removePromoCode(
      @RequestParam String orderOfferCode,
      @ModelAttribute CartSummary cartSummary,
      ModelMap model,
      HttpServletRequest request) {
    Order currentCartOrder = retrieveCartOrder(request, model);
    try {
      currentCartOrder =
          cartService.removeOfferCode(
              currentCartOrder, offerService.lookupOfferCodeByCode(orderOfferCode), true);
    } catch (PricingException e) {
      model.addAttribute("error", "remove");
      LOG.error(
          "An error occurred while removing a promo from the cart: (" + orderOfferCode + ")", e);
    }
    cartSummary.setOrderDiscounts(currentCartOrder.getTotalAdjustmentsValue().getAmount());

    return "redirect:/basket/viewCart.htm";
  }
  /*
   * The addItem method adds a product items with one or more quantity to the cart by adding thes
   * item to a list and calling the addItems method.
   */
  @RequestMapping(
      value = "/addItem.htm",
      method = {RequestMethod.GET, RequestMethod.POST})
  public String addItem(
      @RequestParam(required = false) Boolean ajax,
      @ModelAttribute AddToCartItem addToCartItem,
      BindingResult errors,
      ModelMap model,
      HttpServletRequest request) {
    if (ajax == null) {
      ajax = false;
    }

    /*
    new AddToCartItemsValidator().validate(addToCartItems, errors);
    if (errors.hasErrors()) {
        return refererRedirect(model, errors, request, ajax);
    }
     */

    Order currentCartOrder = retrieveCartOrder(request, model);
    List<OrderItem> orderItemsAdded = new ArrayList<OrderItem>();

    if (addToCartItem.getQuantity() > 0) {
      try {
        OrderItem orderItem;
        if (addToCartItem.getSkuId() == 180) {
          BundleOrderItemRequest itemRequest = new BundleOrderItemRequest();
          DiscreteOrderItemRequest discreteRequest1 =
              cartService.createDiscreteOrderItemRequest(
                  addToCartItem.getSkuId(),
                  addToCartItem.getProductId(),
                  addToCartItem.getCategoryId(),
                  addToCartItem.getQuantity());
          DiscreteOrderItemRequest discreteRequest2 =
              cartService.createDiscreteOrderItemRequest(
                  11L, null, null, addToCartItem.getQuantity());
          itemRequest.getDiscreteOrderItems().add(discreteRequest1);
          itemRequest.getDiscreteOrderItems().add(discreteRequest2);
          itemRequest.setName("Havaletta Bundle");
          itemRequest.setQuantity(1);
          if (addToCartItem.getOrderId() != null) {
            orderItem =
                cartService.addBundleItemToOrder(
                    cartService.findOrderById(addToCartItem.getOrderId()), itemRequest);
          } else {
            orderItem = cartService.addBundleItemToOrder(currentCartOrder, itemRequest);
          }
        } else {
          if (addToCartItem.getOrderId() != null) {
            orderItem =
                cartService.addSkuToOrder(
                    addToCartItem.getOrderId(),
                    addToCartItem.getSkuId(),
                    addToCartItem.getProductId(),
                    addToCartItem.getCategoryId(),
                    addToCartItem.getQuantity());
          } else {
            orderItem =
                cartService.addSkuToOrder(
                    currentCartOrder.getId(),
                    addToCartItem.getSkuId(),
                    addToCartItem.getProductId(),
                    addToCartItem.getCategoryId(),
                    addToCartItem.getQuantity());
          }
        }
        orderItemsAdded.add(orderItem);
      } catch (PricingException e) {
        LOG.error("Unable to price the order: (" + currentCartOrder.getId() + ")", e);
      }
    }

    model.addAttribute("orderItemsAdded", orderItemsAdded);

    if (!ajax) {
      return addItemViewRedirect ? "redirect:" + addItemView : addItemView;
    } else {
      return "catalog/fragments/addToCartModal";
    }
  }