Exemple #1
0
        public async Task <IActionResult> CheckoutBasketAsync([FromBody] BasketCheckoutDto basketCheckout)
        {
            try
            {
                var basket = await _basketRepository.GetBasketById(basketCheckout.BasketId);

                if (basket == null)
                {
                    return(BadRequest());
                }
                BasketCheckoutMessage basketCheckoutMessage = _mapper.Map <BasketCheckoutMessage>(basketCheckout);
                basketCheckoutMessage.BasketLines = new List <BasketLineMessage>();
                int total = 0;
                foreach (var b in basket.BasketLines)
                {
                    var basketLineMessage = new BasketLineMessage
                    {
                        BasketLineId = b.BasketLineId,
                        Price        = b.Price,
                        TicketAmount = b.TicketAmount
                    };
                    total += b.Price * b.TicketAmount;
                    basketCheckoutMessage.BasketLines.Add(basketLineMessage);
                }
                Discount discount = null;
                if (basket.DiscountId.HasValue)
                {
                    discount = await _discountService.GetDiscount(basket.DiscountId.Value);
                }
                if (discount != null)
                {
                    basketCheckoutMessage.BasketTotal = total - discount.Amount;
                }
                else
                {
                    basketCheckoutMessage.BasketTotal = total;
                }

                try
                {
                    ProductPriceChangedIntegrationEvent queueData = new ProductPriceChangedIntegrationEvent
                                                                        (basketCheckoutMessage.BasketId, basketCheckoutMessage.BasketTotal, basketCheckoutMessage.UserId);
                    _eventBus.Publish(queueData);
                }
                catch (Exception e)
                {
                    Console.WriteLine(e);
                    throw;
                }
                await _basketRepository.ClearBasket(basketCheckout.BasketId);

                return(Accepted(basketCheckoutMessage));
            }
            catch (Exception e)
            {
                return(StatusCode(StatusCodes.Status500InternalServerError, e.StackTrace));
            }
        }
        private async Task OnCheckoutMessageReceived(Message message, CancellationToken arg2)
        {
            using var scope = logger.BeginScope("Processing message for trace {TraceId}", message.CorrelationId);

            var body = Encoding.UTF8.GetString(message.Body);//json from service bus

            //save order with status not paid
            BasketCheckoutMessage basketCheckoutMessage = JsonConvert.DeserializeObject <BasketCheckoutMessage>(body);

            Guid orderId = Guid.NewGuid();

            Order order = new Order
            {
                UserId      = basketCheckoutMessage.UserId,
                Id          = orderId,
                OrderPaid   = false,
                OrderPlaced = DateTime.Now,
                OrderTotal  = basketCheckoutMessage.BasketTotal
            };

            await _orderRepository.AddOrder(order);

            logger.LogDebug("Created order {OrderId} for user {UserId}", orderId, basketCheckoutMessage.UserId);

            //send order payment request message
            OrderPaymentRequestMessage orderPaymentRequestMessage = new OrderPaymentRequestMessage
            {
                CardExpiration = basketCheckoutMessage.CardExpiration,
                CardName       = basketCheckoutMessage.CardName,
                CardNumber     = basketCheckoutMessage.CardNumber,
                OrderId        = orderId,
                Total          = basketCheckoutMessage.BasketTotal
            };

            try
            {
                await _messageBus.PublishMessage(orderPaymentRequestMessage, orderPaymentRequestMessageTopic, message.CorrelationId);
            }
            catch (Exception e)
            {
                Console.WriteLine(e);
                throw;
            }
        }
        private async Task OnCheckoutMessageReceived(Message message,
                                                     CancellationToken arg2)
        {
            var body = Encoding.UTF8.GetString(message.Body);//json from service bus

            // Save order with status "not paid"
            BasketCheckoutMessage basketCheckoutMessage =
                JsonConvert.DeserializeObject <BasketCheckoutMessage>(body);

            using (var scope = _scopeFactory.CreateScope())
            {
                var tokenValidationService = scope.ServiceProvider
                                             .GetRequiredService <TokenValidationService>();

                if (!await tokenValidationService.ValidateTokenAsync(
                        basketCheckoutMessage.SecurityContext.AccessToken,
                        message.SystemProperties.EnqueuedTimeUtc))
                {
                    // log, cleanup, ... but don't throw an exception as that will result
                    // in the message not being regarded as handled.
                    return;
                }
            }

            var orderId = Guid.NewGuid();

            var order = new Order
            {
                UserId      = basketCheckoutMessage.UserId,
                Id          = orderId,
                OrderPaid   = false,
                OrderPlaced = DateTime.Now,
                OrderTotal  = basketCheckoutMessage.BasketTotal
            };

            await _orderRepository.AddOrder(order);

            // Trigger payment service by sending a new message.
            // Functionality not included in demo on purpose.
        }
        private async Task <bool> ProcessAsync(string body)
        {
            //save order with status not paid
            BasketCheckoutMessage basketCheckoutMessage = JsonConvert.DeserializeObject <BasketCheckoutMessage>(body);

            Guid orderId = Guid.NewGuid();

            Order order = new Order
            {
                UserId      = basketCheckoutMessage.UserId,
                Id          = orderId,
                OrderPaid   = false,
                OrderPlaced = DateTime.Now,
                OrderTotal  = basketCheckoutMessage.BasketTotal
            };

            await orderRepository.AddOrder(order);

            //send order payment request message
            OrderPaymentRequestMessage orderPaymentRequestMessage = new OrderPaymentRequestMessage
            {
                CardExpiration = basketCheckoutMessage.CardExpiration,
                CardName       = basketCheckoutMessage.CardName,
                CardNumber     = basketCheckoutMessage.CardNumber,
                OrderId        = orderId,
                Total          = basketCheckoutMessage.BasketTotal
            };

            try
            {
                await messageBus.PublishMessage(orderPaymentRequestMessage, orderPaymentRequestMessageQueue);
            }
            catch (Exception e)
            {
                Console.WriteLine(e);
                throw;
            }

            return(true);
        }
        private async Task OnCheckoutMessageReceived(Message message, CancellationToken arg2)
        {
            var body = Encoding.UTF8.GetString(message.Body);//json from service bus

            // Save order with status "not paid"
            BasketCheckoutMessage basketCheckoutMessage = JsonConvert.DeserializeObject <BasketCheckoutMessage>(body);

            var orderId = Guid.NewGuid();

            var order = new Order
            {
                UserId      = basketCheckoutMessage.UserId,
                Id          = orderId,
                OrderPaid   = false,
                OrderPlaced = DateTime.Now,
                OrderTotal  = basketCheckoutMessage.BasketTotal
            };

            await _orderRepository.AddOrder(order);

            // Trigger payment service by sending a new message.
            // Functionality not included in demo on purpose.
        }
        public async Task <IActionResult> CheckoutBasketAsync([FromBody] BasketCheckout basketCheckout)
        {
            try
            {
                //based on basket checkout, fetch the basket lines from repo
                var basket = await basketRepository.GetBasketById(basketCheckout.BasketId);

                if (basket == null)
                {
                    return(BadRequest());
                }

                BasketCheckoutMessage basketCheckoutMessage = mapper.Map <BasketCheckoutMessage>(basketCheckout);
                basketCheckoutMessage.BasketLines = new List <BasketLineMessage>();
                int total = 0;

                foreach (var b in basket.BasketLines)
                {
                    var basketLineMessage = new BasketLineMessage
                    {
                        BasketLineId = b.BasketLineId,
                        Price        = b.Price,
                        TicketAmount = b.TicketAmount
                    };

                    total += b.Price * b.TicketAmount;

                    basketCheckoutMessage.BasketLines.Add(basketLineMessage);
                }

                //apply discount by talking to the discount service
                Coupon coupon = null;

                //if (basket.CouponId.HasValue)
                //    coupon = await discountService.GetCoupon(basket.CouponId.Value);

                if (basket.CouponId.HasValue)
                {
                    coupon = await discountService.GetCouponWithError(basket.CouponId.Value);
                }

                if (coupon != null)
                {
                    basketCheckoutMessage.BasketTotal = total - coupon.Amount;
                }
                else
                {
                    basketCheckoutMessage.BasketTotal = total;
                }

                try
                {
                    await messageBus.PublishMessage(basketCheckoutMessage, "checkoutmessage");
                }
                catch (Exception e)
                {
                    Console.WriteLine(e);
                    throw;
                }

                await basketRepository.ClearBasket(basketCheckout.BasketId);

                return(Accepted(basketCheckoutMessage));
            }
            catch (BrokenCircuitException ex)
            {
                string message = ex.Message;
                return(StatusCode(StatusCodes.Status500InternalServerError, ex.StackTrace));
            }
            catch (Exception e)
            {
                return(StatusCode(StatusCodes.Status500InternalServerError, e.StackTrace));
            }
        }
        public async Task <IActionResult> CheckoutBasketAsync([FromBody] BasketCheckout basketCheckout)
        {
            using var scope = logger.BeginScope("Checking out basket {BasketId}", basketCheckout.BasketId);

            try
            {
                //based on basket checkout, fetch the basket lines from repo
                var basket = await basketRepository.GetBasketById(basketCheckout.BasketId);

                if (basket == null)
                {
                    logger.LogWarning("Basket was not found");
                    return(BadRequest());
                }

                logger.LogDebug("Loaded basket");

                BasketCheckoutMessage basketCheckoutMessage = mapper.Map <BasketCheckoutMessage>(basketCheckout);
                basketCheckoutMessage.BasketLines = new List <BasketLineMessage>();
                int total = 0;

                foreach (var b in basket.BasketLines)
                {
                    var basketLineMessage = new BasketLineMessage
                    {
                        BasketLineId = b.BasketLineId,
                        Price        = b.Price,
                        TicketAmount = b.TicketAmount
                    };

                    total += b.Price * b.TicketAmount;

                    basketCheckoutMessage.BasketLines.Add(basketLineMessage);
                }

                //apply discount by talking to the discount service
                Coupon coupon = null;

                var channel = GrpcChannel.ForAddress("https://localhost:5007");

                DiscountService discountService = new DiscountService(new Discounts.DiscountsClient(channel));
                if (basket.CouponId.HasValue)
                {
                    coupon = await discountService.GetCoupon(basket.CouponId.Value);
                }

                if (coupon != null)
                {
                    logger.LogDebug("Applying discount {DiscountAmount} from {CouponId}", coupon.Amount, basket.CouponId.Value);
                    basketCheckoutMessage.BasketTotal = total - coupon.Amount;
                }
                else
                {
                    logger.LogDebug("No discount to apply");
                    basketCheckoutMessage.BasketTotal = total;
                }

                try
                {
                    await messageBus.PublishMessage(basketCheckoutMessage, "checkoutmessage",
                                                    Activity.Current.TraceId.ToString());

                    logger.LogDebug("Published checkout message");
                }
                catch (Exception e)
                {
                    logger.LogError(e, "Unable to publish checkout message");
                    throw;
                }

                await basketRepository.ClearBasket(basketCheckout.BasketId);

                return(Accepted(basketCheckoutMessage));
            }
            catch (Exception e)
            {
                logger.LogError(e, "An exception occurred when checking out the basket");

                return(StatusCode(StatusCodes.Status500InternalServerError, e.StackTrace));
            }
        }