Example #1
0
        /// <summary>
        /// Places a new <c>Order</c>.
        /// </summary>
        /// <param name="options">Options for creating a new <c>StoreContext</c>.</param>
        /// <param name="orderId">The ID of a previously saved <c>Order</c>.</param>
        /// <param name="maxQuantity">The maximum amount of <c>Product</c> that may be present in an <c>Order</c>.</param>
        /// <returns>A <c>PlaceOrderResult</c> detailing whether the operation completed successfully.</returns>
        public static PlaceOrderResult PlaceOrder(this DbContextOptions <StoreContext> options, Guid?orderId, int maxQuantity)
        {
            if (orderId == null)
            {
                throw new NullReferenceException("Missing orderId");
            }
            using (var db = new StoreContext(options))
            {
                var order = db.GetOrderById(orderId);
                if (order == null)
                {
                    return(PlaceOrderResult.OrderNotFound);
                }

                if (order.OrderLineItems.Count() == 0)
                {
                    return(PlaceOrderResult.NoLineItems);
                }

                var totalOrderPrice   = 0.0;
                var totalItemQuantity = 0;

                var location = order.Location;
                using (var transaction = db.Database.BeginTransaction())
                {
                    foreach (var lineItem in order.OrderLineItems)
                    {
                        var locationInventory = db.FindInventoryId(location, lineItem.Product);
                        if (locationInventory == null)
                        {
                            return(PlaceOrderResult.OutOfStock);
                        }
                        var newStockQuantity = locationInventory.TryAdjustQuantity(-lineItem.Quantity);
                        if (newStockQuantity == null)
                        {
                            transaction.Rollback();
                            return(PlaceOrderResult.OutOfStock);
                        }

                        var lineItemPrice = lineItem.Quantity * lineItem.Product.Price;
                        totalOrderPrice       += lineItemPrice;
                        lineItem.AmountCharged = lineItemPrice;
                        totalItemQuantity     += lineItem.Quantity;
                        db.SaveChanges();
                    }
                    if (totalItemQuantity > maxQuantity)
                    {
                        return(PlaceOrderResult.HighQuantityRejection);
                    }
                    order.AmountPaid    = totalOrderPrice;
                    order.TimeSubmitted = DateTime.Now;
                    db.SaveChanges();
                    transaction.Commit();
                }
                return(PlaceOrderResult.Ok);
            }
        }