Beispiel #1
0
        public async Task <IActionResult> Save(OrderDTO orderDto)
        {
            var order = _orderRepository.GetOrderInclById(orderDto.Id);

            if (order == null)
            {
                return(BadRequest("Order not found."));
            }

            // Ensure that email is provided for order created by guest user
            if (String.IsNullOrEmpty(order.CustomerId) && String.IsNullOrEmpty(orderDto.DeliveryDetails.Email))
            {
                ModelState.AddModelError("", "Email is not provided.");
            }

            if (!ModelState.IsValid)
            {
                _breadcrumbNavBuilder.CreateForNode("CPanelOrderEdit", new { orderId = order.Id, orderName = ("Order #" + order.Id).ToString() }, this);
                return(View("Edit", orderDto));
            }

            var admin = await _userManager.GetUserAsync(User);

            // Preserve original user comment
            var tempComment = order.DeliveryDetails.Comment;

            // Set delivery & payment details
            Object2ObjectMappings.OrderDetailsDtoToOrder(orderDto.DeliveryDetails, order);

            // Recalculate delivery fee
            order.DeliveryFee             = DeliveryFeeCalculator.Calculate(order.DeliveryDetails.DeliveryMethodType);
            order.DeliveryDetails.Comment = tempComment;

            // Retireve changes and log
            var changeLogs = _auditTrailService.RetrieveAndLogChanges();

            foreach (var changeLog in changeLogs)
            {
                order.ChangeHistory.Add(new OrderChangeLog {
                    ChangeLog = changeLog, Order = order
                });
            }

            // Update last edit timestamp
            order.LastModifiedById = admin.Id;
            order.LastModifiedOn   = DateTime.UtcNow;

            _orderRepository.SaveChanges();

            return(RedirectToAction("AdminView", new { id = orderDto.Id }));
        }
Beispiel #2
0
        public IList <DeliveryOption> GetOptions(DateTime dtStart, int nextDays, DeliveryFeeCalculator defaultCalc, DateTimeTerm openingHours)
        {
            var result = new List <DeliveryOption>();

            var calc = Calculator ?? defaultCalc;

            if (calc == null)
            {
                return(result);
            }

            IList <DateTimePair> pairs;

            if (SameAsOpeningHours)
            {
                pairs = openingHours.GetDateTimePairs(dtStart, nextDays);
            }
            else if (DateTimes != null)
            {
                pairs = DateTimes.GetDateTimePairs(dtStart, nextDays);
            }
            else
            {
                pairs = new List <DateTimePair>();
            }

            foreach (var p in pairs)
            {
                result.Add(new DeliveryOption()
                {
                    From = p.From,
                    To   = p.To,
                    ReferenceTimePonitType = p.ReferenceTimePonitType,
                    DivisionType           = p.DivisionType,
                    DivisionMinutes        = p.DivisionMinutes,
                    Areas      = Areas,
                    Calculator = calc
                });
            }

            return(result);
        }
Beispiel #3
0
        public void TestDeliveryFeeCalculator()
        {
            var calc = new DeliveryFeeCalculator();

            //combine
            calc.Rules.Add(new BasicDeliveryFeeRule()
            {
                Areas           = { "nz:auckland:auckland:auckland-city" },
                DistanceTo      = 20,
                OrderAmountFrom = 50,
                Fee             = 50
            });
            calc.Rules.Add(new BasicDeliveryFeeRule()
            {
                Areas           = { "nz:auckland:auckland:north-shore" },
                DistanceTo      = 30,
                OrderAmountFrom = 70,
                Fee             = 51
            });
            //with order amount
            calc.Rules.Add(new BasicDeliveryFeeRule()
            {
                OrderAmountFrom = 30,
                OrderAmountTo   = 60,
                Fee             = 42
            });
            calc.Rules.Add(new BasicDeliveryFeeRule()
            {
                OrderAmountTo = 60,
                Fee           = 41
            });
            calc.Rules.Add(new BasicDeliveryFeeRule()
            {
                OrderAmountFrom = 30,
                Fee             = 40
            });
            //with distance
            calc.Rules.Add(new BasicDeliveryFeeRule()
            {
                DistanceFrom = 2000,
                DistanceTo   = 3000,
                Fee          = 32
            });
            calc.Rules.Add(new BasicDeliveryFeeRule()
            {
                DistanceTo = 3000,
                Fee        = 31
            });
            calc.Rules.Add(new BasicDeliveryFeeRule()
            {
                DistanceFrom = 2000,
                Fee          = 30
            });
            //area
            calc.Rules.Add(new BasicDeliveryFeeRule()
            {
                Areas = { "nz:auckland:auckland:auckland-city" },
                Fee   = 21
            });
            calc.Rules.Add(new BasicDeliveryFeeRule()
            {
                Areas = { "nz:auckland:auckland" },
                Fee   = 20
            });
            //fixed
            calc.Rules.Add(new BasicDeliveryFeeRule()
            {
                Fee = 10
            });


            Assert.AreEqual(10, calc.Calculate(DateTime.Now, null, null, null));
            Assert.AreEqual(20, calc.Calculate(DateTime.Now, "nz:auckland:auckland:central-auckland", null, null));
            Assert.AreEqual(21, calc.Calculate(DateTime.Now, "nz:auckland:auckland:auckland-city", null, null));
            Assert.AreEqual(30, calc.Calculate(DateTime.Now, null, 3001, null));
            Assert.AreEqual(31, calc.Calculate(DateTime.Now, null, 1999, null));
            Assert.AreEqual(32, calc.Calculate(DateTime.Now, null, 2000, null));
            Assert.AreEqual(32, calc.Calculate(DateTime.Now, null, 3000, null));
            Assert.AreEqual(40, calc.Calculate(DateTime.Now, null, null, 61));
            Assert.AreEqual(41, calc.Calculate(DateTime.Now, null, null, 29));
            Assert.AreEqual(42, calc.Calculate(DateTime.Now, null, null, 30));
            Assert.AreEqual(42, calc.Calculate(DateTime.Now, null, null, 60));
            Assert.AreEqual(50, calc.Calculate(DateTime.Now, "nz:auckland:auckland:auckland-city", 19, 51));
            Assert.AreEqual(51, calc.Calculate(DateTime.Now, "nz:auckland:auckland:north-shore", 29, 71));
        }
Beispiel #4
0
        public async Task <IActionResult> CheckoutSummary([FromForm] OrderDetailsDTO deliveryDetailsDTO)
        {
            var user = await _userManager.GetUserAsync(User);

            if (user != null)
            {
                // check if account is restricted (read-only)
                if (user.IsBlocked)
                {
                    return(BadRequest("Your request can't be processed as you account has been restricted."));
                }
            }
            else
            {
                if (String.IsNullOrEmpty(deliveryDetailsDTO.Email))
                {
                    ModelState.AddModelError("", "Email is not provided.");
                }
            }

            if (!ModelState.IsValid)
            {
                var msg = String.Join(" \r\n ", ModelState.Values.SelectMany(v => v.Errors).Select(e => e.ErrorMessage));
                return(BadRequest(msg));
            }

            try
            {
                var cart = _cartManager.GetCart();

                // redirect to cart if it's empty
                if (_cartManager.GetCart() == null)
                {
                    return(BadRequest("Cart is empty. Please try again."));
                }

                if (_cartManager.GetCart().ItemCount == 0)
                {
                    return(BadRequest("Cart is empty. Please try again."));
                }

                // create order draft (dto)
                var tempOrder = new OrderDTO()
                {
                    DeliveryDetails = deliveryDetailsDTO,
                    Items           = cart.Items.Select(c => new OrderItemDTO
                    {
                        Product = new ProductDTO
                        {
                            Name  = c.Product.Name,
                            Price = c.Product.SalePrice,
                            Id    = c.Product.Id
                        },
                        Quantity = c.Quantity
                    })
                                      .ToList(),
                    NoUserAccount = (user == null),
                    DeliveryFee   = DeliveryFeeCalculator.Calculate(deliveryDetailsDTO.DeliveryMethodType)
                };

                // write temp order object to cache and assign confirmation key to be sent to client
                var orderConfirmationKey = WriteToCache(tempOrder);

                // generate markup to be show in order confirmation
                var viewMarkup = await _viewMarkupExtractor.MarkupToString(this.ControllerContext, "OrderPreview", tempOrder, this.TempData);

                return(new JsonResult(new { summaryMarkup = viewMarkup, confirmationKey = orderConfirmationKey }));
            }
            catch (Exception ex)
            {
                var userId = _userManager.GetUserId(User);

                _logger.LogError("Order validation failed (user ID: " + userId + "). " + ex.ToString());
                return(BadRequest("Unexpected error has occured. Please try again later.  \r\n If problem persists, please contact administrator."));
            }
        }
Beispiel #5
0
        public async Task <IActionResult> CheckoutConfirm([FromRoute] string confirmationKey)
        {
            try
            {
                var userId = _userManager.GetUserId(User);

                // validate confirmation key
                if (String.IsNullOrEmpty(confirmationKey))
                {
                    return(BadRequest("Missing confirmation key."));
                }

                // try to retrieve temp order from cache
                var tempOrder = ReadFromCache(confirmationKey);

                if (tempOrder == null)
                {
                    return(BadRequest("Temp order not found."));
                }

                // create order
                var order = new Order(tempOrder.DeliveryDetails.DeliveryMethodType)
                {
                    CreatedOn  = DateTime.UtcNow,
                    CustomerId = userId,
                    Status     = OrderStatus.Created
                };

                // append all items
                foreach (var tempItem in tempOrder.Items)
                {
                    var productInDb = _productRepository.GetProductById(tempItem.Product.Id);

                    if (productInDb != null &&
                        productInDb.NumberInStock >= tempItem.Quantity &&
                        productInDb.IsActive &&
                        productInDb.IsAvailable)
                    {
                        order.Items.Add(new OrderItem
                        {
                            Product       = productInDb,
                            ProductId     = productInDb.Id,
                            PurchasePrice = productInDb.SalePrice,
                            Quantity      = tempItem.Quantity
                        });
                    }
                }

                // check if email has been provided for guest user
                if (String.IsNullOrEmpty(userId))
                {
                    if (String.IsNullOrEmpty(tempOrder.DeliveryDetails.Email))
                    {
                        return(BadRequest("No email address provided for guest user's order."));
                    }

                    order.DeliveryDetails.EmailAddress = tempOrder.DeliveryDetails.Email;
                }

                // set basic delivery details
                order.DeliveryFee = DeliveryFeeCalculator.Calculate(tempOrder.DeliveryDetails.DeliveryMethodType);

                // set delivery-specific details
                Object2ObjectMappings.OrderDetailsDtoToOrder(tempOrder.DeliveryDetails, order);

                // check consistency or order amount (prevents user from accidentally ordering items for which the price has just changed)
                if (order.OrderAmountTotal != tempOrder.OrderAmountTotal)
                {
                    return(BadRequest("Price of some items you are trying to order might have changed."));
                }

                // persist changes
                _orderRepository.AddOrder(order);

                if (_orderRepository.SaveChanges() > 0)
                {
                    _cartManager.ResetCart();
                    _memoryCache.Remove(confirmationKey);

                    await SendOrderConfirmation(order);
                }

                // return order id
                return(Ok(new { orderId = order.Id }));
            }
            catch (Exception ex)
            {
                var userId = _userManager.GetUserId(User);

                _logger.LogError("Order validation failed (user ID: " + userId + "). " + ex.ToString());
                return(BadRequest("Unexpected error has occured. Please try again later."));
            }
        }