private async Task <decimal> ApplyDiscount(User user, Cart cart) { decimal discount = 0; if (!string.IsNullOrWhiteSpace(cart.CouponCode)) { var cartInfoForCoupon = new CartInfoForCoupon { Items = cart.Items.Select(x => new CartItemForCoupon { ProductId = x.ProductId, Quantity = x.Quantity }).ToList() }; var couponValidationResult = await _couponService.Validate(cart.CouponCode, cartInfoForCoupon); if (couponValidationResult.Succeeded) { discount = couponValidationResult.DiscountAmount; _couponService.AddCouponUsage(user.Id, couponValidationResult.CouponId); } else { throw new ApplicationException($"Unable to apply coupon {cart.CouponCode}. {couponValidationResult.ErrorMessage}"); } } return(discount); }
public async Task <Result <Order> > CreateOrder(User user, string paymentMethod, decimal paymentFeeAmount, string shippingMethodName, Address billingAddress, Address shippingAddress, OrderStatus orderStatus = OrderStatus.New) { var cart = _cartRepository .Query() .Include(c => c.Items).ThenInclude(x => x.Product) .Where(x => x.UserId == user.Id && x.IsActive).FirstOrDefault(); if (cart == null) { return(Result.Fail <Order>($"Cart of user {user.Id} cannot be found")); } var checkingDiscountResult = await CheckForDiscountIfAny(user, cart); if (!checkingDiscountResult.Succeeded) { return(Result.Fail <Order>(checkingDiscountResult.ErrorMessage)); } var validateShippingMethodResult = await ValidateShippingMethod(shippingMethodName, shippingAddress, cart); if (!validateShippingMethodResult.Success) { return(Result.Fail <Order>(validateShippingMethodResult.Error)); } var shippingMethod = validateShippingMethodResult.Value; var orderBillingAddress = new OrderAddress() { AddressLine1 = billingAddress.AddressLine1, AddressLine2 = billingAddress.AddressLine2, ContactName = billingAddress.ContactName, CountryId = billingAddress.CountryId, StateOrProvinceId = billingAddress.StateOrProvinceId, DistrictId = billingAddress.DistrictId, City = billingAddress.City, ZipCode = billingAddress.ZipCode, Phone = billingAddress.Phone }; var orderShippingAddress = new OrderAddress() { AddressLine1 = shippingAddress.AddressLine1, AddressLine2 = shippingAddress.AddressLine2, ContactName = shippingAddress.ContactName, CountryId = shippingAddress.CountryId, StateOrProvinceId = shippingAddress.StateOrProvinceId, DistrictId = shippingAddress.DistrictId, City = shippingAddress.City, ZipCode = shippingAddress.ZipCode, Phone = shippingAddress.Phone }; var order = new Order { CreatedOn = DateTimeOffset.Now, CreatedById = user.Id, BillingAddress = orderBillingAddress, ShippingAddress = orderShippingAddress, PaymentMethod = paymentMethod, PaymentFeeAmount = paymentFeeAmount }; foreach (var cartItem in cart.Items) { if (cartItem.Product.StockTrackingIsEnabled && cartItem.Product.StockQuantity < cartItem.Quantity) { return(Result.Fail <Order>($"There are only {cartItem.Product.StockQuantity} items available for {cartItem.Product.Name}")); } var taxPercent = await _taxService.GetTaxPercent(cartItem.Product.TaxClassId, shippingAddress.CountryId, shippingAddress.StateOrProvinceId, shippingAddress.ZipCode); var productPrice = cartItem.Product.Price; if (cart.IsProductPriceIncludeTax) { productPrice = productPrice / (1 + (taxPercent / 100)); } var orderItem = new OrderItem { Product = cartItem.Product, ProductPrice = productPrice, Quantity = cartItem.Quantity, TaxPercent = taxPercent, TaxAmount = cartItem.Quantity * (productPrice * taxPercent / 100) }; var discountedItem = checkingDiscountResult.DiscountedProducts.FirstOrDefault(x => x.Id == cartItem.ProductId); if (discountedItem != null) { orderItem.DiscountAmount = discountedItem.DiscountAmount; } order.AddOrderItem(orderItem); if (cartItem.Product.StockTrackingIsEnabled) { cartItem.Product.StockQuantity = cartItem.Product.StockQuantity - cartItem.Quantity; } } order.OrderStatus = orderStatus; order.CouponCode = checkingDiscountResult.CouponCode; order.CouponRuleName = cart.CouponRuleName; order.DiscountAmount = checkingDiscountResult.DiscountAmount; order.ShippingFeeAmount = shippingMethod.Price; order.ShippingMethod = shippingMethod.Name; order.TaxAmount = order.OrderItems.Sum(x => x.TaxAmount); order.SubTotal = order.OrderItems.Sum(x => x.ProductPrice * x.Quantity); order.SubTotalWithDiscount = order.SubTotal - checkingDiscountResult.DiscountAmount; order.OrderTotal = order.SubTotal + order.TaxAmount + order.ShippingFeeAmount + order.PaymentFeeAmount - order.DiscountAmount; _orderRepository.Add(order); cart.IsActive = false; var vendorIds = cart.Items.Where(x => x.Product.VendorId.HasValue).Select(x => x.Product.VendorId.Value).Distinct(); if (vendorIds.Any()) { order.IsMasterOrder = true; } foreach (var vendorId in vendorIds) { var subOrder = new Order { CreatedOn = DateTimeOffset.Now, CreatedById = user.Id, BillingAddress = orderBillingAddress, ShippingAddress = orderShippingAddress, VendorId = vendorId, Parent = order }; foreach (var cartItem in cart.Items.Where(x => x.Product.VendorId == vendorId)) { var taxPercent = await _taxService.GetTaxPercent(cartItem.Product.TaxClassId, shippingAddress.CountryId, shippingAddress.StateOrProvinceId, shippingAddress.ZipCode); var productPrice = cartItem.Product.Price; if (cart.IsProductPriceIncludeTax) { productPrice = productPrice / (1 + (taxPercent / 100)); } var orderItem = new OrderItem { Product = cartItem.Product, ProductPrice = productPrice, Quantity = cartItem.Quantity, TaxPercent = taxPercent, TaxAmount = cartItem.Quantity * (productPrice * taxPercent / 100) }; if (cart.IsProductPriceIncludeTax) { orderItem.ProductPrice = orderItem.ProductPrice - orderItem.TaxAmount; } subOrder.AddOrderItem(orderItem); } subOrder.SubTotal = subOrder.OrderItems.Sum(x => x.ProductPrice * x.Quantity); subOrder.TaxAmount = subOrder.OrderItems.Sum(x => x.TaxAmount); subOrder.OrderTotal = subOrder.SubTotal + subOrder.TaxAmount + subOrder.ShippingFeeAmount - subOrder.DiscountAmount; _orderRepository.Add(subOrder); } using (var transaction = _orderRepository.BeginTransaction()) { _orderRepository.SaveChanges(); _couponService.AddCouponUsage(user.Id, order.Id, checkingDiscountResult); _orderRepository.SaveChanges(); transaction.Commit(); } // await _orderEmailService.SendEmailToUser(user, order); return(Result.Ok(order)); }
public async Task CreateOrder(User user, Address billingAddress, Address shippingAddress) { var cart = _cartRepository .Query() .Include(c => c.Items).ThenInclude(x => x.Product) .Where(x => x.UserId == user.Id && x.IsActive).FirstOrDefault(); if (cart == null) { throw new ApplicationException($"Cart of user {user.Id} can no be found"); } decimal discount = 0; if (!string.IsNullOrWhiteSpace(cart.CouponCode)) { var cartInfoForCoupon = new CartInfoForCoupon { Items = cart.Items.Select(x => new CartItemForCoupon { ProductId = x.ProductId, Quantity = x.Quantity }).ToList() }; var couponValidationResult = await _couponService.Validate(cart.CouponCode, cartInfoForCoupon); if (couponValidationResult.Succeeded) { discount = couponValidationResult.DiscountAmount; _couponService.AddCouponUsage(user.Id, couponValidationResult.CouponId); } else { throw new ApplicationException($"Unable to apply coupon {cart.CouponCode}. {couponValidationResult.ErrorMessage}"); } } var orderBillingAddress = new OrderAddress() { AddressLine1 = billingAddress.AddressLine1, ContactName = billingAddress.ContactName, CountryId = billingAddress.CountryId, StateOrProvinceId = billingAddress.StateOrProvinceId, DistrictId = billingAddress.DistrictId, Phone = billingAddress.Phone }; var orderShippingAddress = new OrderAddress() { AddressLine1 = shippingAddress.AddressLine1, ContactName = shippingAddress.ContactName, CountryId = shippingAddress.CountryId, StateOrProvinceId = shippingAddress.StateOrProvinceId, DistrictId = shippingAddress.DistrictId, Phone = shippingAddress.Phone }; var order = new Order { CreatedOn = DateTimeOffset.Now, CreatedById = user.Id, BillingAddress = orderBillingAddress, ShippingAddress = orderShippingAddress }; foreach (var cartItem in cart.Items) { var orderItem = new OrderItem { Product = cartItem.Product, ProductPrice = cartItem.Product.Price, Quantity = cartItem.Quantity }; order.AddOrderItem(orderItem); } order.CouponCode = cart.CouponCode; order.CouponRuleName = cart.CouponRuleName; order.Discount = discount; order.SubTotal = order.OrderItems.Sum(x => x.ProductPrice * x.Quantity); order.SubTotalWithDiscount = order.SubTotal - discount; _orderRepository.Add(order); cart.IsActive = false; var vendorIds = cart.Items.Where(x => x.Product.VendorId.HasValue).Select(x => x.Product.VendorId.Value).Distinct(); foreach (var vendorId in vendorIds) { var subOrder = new Order { CreatedOn = DateTimeOffset.Now, CreatedById = user.Id, BillingAddress = orderBillingAddress, ShippingAddress = orderShippingAddress, VendorId = vendorId, Parent = order }; foreach (var cartItem in cart.Items.Where(x => x.Product.VendorId == vendorId)) { var orderItem = new OrderItem { Product = cartItem.Product, ProductPrice = cartItem.Product.Price, Quantity = cartItem.Quantity }; subOrder.AddOrderItem(orderItem); } subOrder.SubTotal = subOrder.OrderItems.Sum(x => x.ProductPrice * x.Quantity); _orderRepository.Add(subOrder); } _orderRepository.SaveChange(); }
public async Task <Result <Order> > CreateOrder(long cartId, string paymentMethod, decimal paymentFeeAmount, string shippingMethodName, Address billingAddress, Address shippingAddress, OrderStatus orderStatus = OrderStatus.New) { var cart = _cartRepository .Query() .Include(c => c.Items).ThenInclude(x => x.Product) .Where(x => x.Id == cartId).FirstOrDefault(); if (cart == null) { return(Result.Fail <Order>($"Cart id {cartId} cannot be found")); } var checkingDiscountResult = await CheckForDiscountIfAny(cart); if (!checkingDiscountResult.Succeeded) { return(Result.Fail <Order>(checkingDiscountResult.ErrorMessage)); } var validateShippingMethodResult = await ValidateShippingMethod(shippingMethodName, shippingAddress, cart); if (!validateShippingMethodResult.Success) { return(Result.Fail <Order>(validateShippingMethodResult.Error)); } var shippingMethod = validateShippingMethodResult.Value; var orderBillingAddress = new OrderAddress() { AddressLine1 = billingAddress.AddressLine1, AddressLine2 = billingAddress.AddressLine2, ContactName = billingAddress.ContactName, CountryId = billingAddress.CountryId, StateOrProvinceId = billingAddress.StateOrProvinceId, DistrictId = billingAddress.DistrictId, City = billingAddress.City, ZipCode = billingAddress.ZipCode, Phone = billingAddress.Phone }; var orderShippingAddress = new OrderAddress() { AddressLine1 = shippingAddress.AddressLine1, AddressLine2 = shippingAddress.AddressLine2, ContactName = shippingAddress.ContactName, CountryId = shippingAddress.CountryId, StateOrProvinceId = shippingAddress.StateOrProvinceId, DistrictId = shippingAddress.DistrictId, City = shippingAddress.City, ZipCode = shippingAddress.ZipCode, Phone = shippingAddress.Phone }; var order = new Order { CustomerId = cart.CustomerId, CreatedOn = DateTimeOffset.Now, CreatedById = cart.CreatedById, LatestUpdatedOn = DateTimeOffset.Now, LatestUpdatedById = cart.CreatedById, BillingAddress = orderBillingAddress, ShippingAddress = orderShippingAddress, PaymentMethod = paymentMethod, PaymentFeeAmount = paymentFeeAmount }; foreach (var cartItem in cart.Items) { //codigo origen, necesairio revisar validaciones para la compra tipo stock etc //if (!cartItem.Product.IsAllowToOrder || !cartItem.Product.IsPublished || cartItem.Product.IsDeleted) //{ // return Result.Fail<Order>($"The product {cartItem.Product.Name} is not available any more"); //} //if (cartItem.Product.StockTrackingIsEnabled && cartItem.Product.StockQuantity < cartItem.Quantity) //{ // return Result.Fail<Order>($"There are only {cartItem.Product.StockQuantity} items available for {cartItem.Product.Name}"); //} var taxPercent = await _taxService.GetTaxPercent(cartItem.Product.TaxClassId, shippingAddress.CountryId, shippingAddress.StateOrProvinceId, shippingAddress.ZipCode); var productPrice = cartItem.Product.Price; if (cart.IsProductPriceIncludeTax) { productPrice = productPrice / (1 + (taxPercent / 100)); } var orderItem = new OrderItem { Product = cartItem.Product, ProductPrice = productPrice, Quantity = cartItem.Quantity, TaxPercent = taxPercent, TaxAmount = cartItem.Quantity * (productPrice * taxPercent / 100) }; var discountedItem = checkingDiscountResult.DiscountedProducts.FirstOrDefault(x => x.Id == cartItem.ProductId); if (discountedItem != null) { orderItem.DiscountAmount = discountedItem.DiscountAmount; } order.AddOrderItem(orderItem); if (cartItem.Product.StockTrackingIsEnabled) { cartItem.Product.StockQuantity = cartItem.Product.StockQuantity - cartItem.Quantity; } } order.OrderStatus = orderStatus; order.OrderNote = cart.OrderNote; order.CouponCode = checkingDiscountResult.CouponCode; order.CouponRuleName = cart.CouponRuleName; order.DiscountAmount = checkingDiscountResult.DiscountAmount; order.ShippingFeeAmount = shippingMethod.Price; order.ShippingMethod = shippingMethod.Name; order.TaxAmount = order.OrderItems.Sum(x => x.TaxAmount); order.SubTotal = order.OrderItems.Sum(x => x.ProductPrice * x.Quantity); order.SubTotalWithDiscount = order.SubTotal - checkingDiscountResult.DiscountAmount; order.OrderTotal = order.SubTotal + order.TaxAmount + order.ShippingFeeAmount + order.PaymentFeeAmount - order.DiscountAmount; _orderRepository.Add(order); cart.IsActive = false; var vendorIds = cart.Items.Where(x => x.Product.VendorId.HasValue).Select(x => x.Product.VendorId.Value).Distinct(); if (vendorIds.Any()) { order.IsMasterOrder = true; } IList <Order> subOrders = new List <Order>(); foreach (var vendorId in vendorIds) { var subOrder = new Order { CustomerId = cart.CustomerId, CreatedOn = DateTimeOffset.Now, CreatedById = cart.CreatedById, LatestUpdatedOn = DateTimeOffset.Now, LatestUpdatedById = cart.CreatedById, BillingAddress = orderBillingAddress, ShippingAddress = orderShippingAddress, VendorId = vendorId, Parent = order }; foreach (var cartItem in cart.Items.Where(x => x.Product.VendorId == vendorId)) { var taxPercent = await _taxService.GetTaxPercent(cartItem.Product.TaxClassId, shippingAddress.CountryId, shippingAddress.StateOrProvinceId, shippingAddress.ZipCode); var productPrice = cartItem.Product.Price; if (cart.IsProductPriceIncludeTax) { productPrice = productPrice / (1 + (taxPercent / 100)); } var orderItem = new OrderItem { Product = cartItem.Product, ProductPrice = productPrice, Quantity = cartItem.Quantity, TaxPercent = taxPercent, TaxAmount = cartItem.Quantity * (productPrice * taxPercent / 100) }; if (cart.IsProductPriceIncludeTax) { orderItem.ProductPrice = orderItem.ProductPrice - orderItem.TaxAmount; } subOrder.AddOrderItem(orderItem); } subOrder.SubTotal = subOrder.OrderItems.Sum(x => x.ProductPrice * x.Quantity); subOrder.TaxAmount = subOrder.OrderItems.Sum(x => x.TaxAmount); subOrder.OrderTotal = subOrder.SubTotal + subOrder.TaxAmount + subOrder.ShippingFeeAmount - subOrder.DiscountAmount; _orderRepository.Add(subOrder); subOrders.Add(subOrder); } using (var transaction = _orderRepository.BeginTransaction()) { _orderRepository.SaveChanges(); await PublishOrderCreatedEvent(order); foreach (var subOrder in subOrders) { await PublishOrderCreatedEvent(subOrder); } _couponService.AddCouponUsage(cart.CustomerId, order.Id, checkingDiscountResult); _orderRepository.SaveChanges(); transaction.Commit(); } //aqui tenemos que borrar el carrito return(Result.Ok(order)); }