public PaymentModule(ICoreService service)
            : base("/payment")
        {
            Get["/"] = _ =>
            {
                return View["Payments/TakePayment", new TransactionViewModel()
                {
                    ApiEnvironment = service.APIEnvironment,
                    RedirectUrl = ConfigurationManager.AppSettings["PublicWebUrl"] + "/payment/redirect-back",
                    Country = "GB" // Default it to help your customers, it's a long list!
                }];
            };

            Get["/redirect-back"] = _ =>
                {
                    // You can fetch the payment method before charging the card to say check the card type
                    var paymentMethod = service.GetPaymentMethod(Request.Query.token);

                    var transaction = service.ProcessPayment(new ProcessPaymentRequest
                    {
                        AmountInDecimal = 1.0m, // Same as saying Amount = 100
                        CurrencyCode = CurrencyCode.GBP,
                        PaymentMethodToken = Request.Query.token
                    });

                    if (transaction.Succeeded)
                    {
                        return View["Payments/Success"];
                    }

                    var viewModel = new TransactionViewModel();

                    viewModel.PopulateFromTransaction(transaction, ConfigurationManager.AppSettings["PublicWebUrl"] + "/payment/redirect-back", service.APIEnvironment);

                    return View["Payments/TakePayment", viewModel];
                };
        }
        public Payment3DSecureModule(ICoreService service)
            : base("/3d-secure")
        {
            Get["/"] = parameters =>
            {
                return View["TakePayment", new TransactionViewModel()
                {
                    ApiEnvironment = service.APIEnvironment,
                    RedirectUrl = ConfigurationManager.AppSettings["PublicWebUrl"] + "/3d-secure/redirect",
                    Country = "GB" // Default it to help your customers, it's a long list!
                }];
            };

            // First redirect from Core saying further processing
            // We then redirect or show the 3d secure form
            Get["/redirect"] = parameters =>
            {
                // You can fetch the payment method before charging the card to say check the card type
                var paymentMethod = service.GetPaymentMethod(Request.Query.token);

                var transaction = service.ProcessPayment(new ProcessPaymentRequest
                {
                    Attempt3DSecure = true,
                    Amount = 100,
                    CurrencyCode = CurrencyCode.GBP,
                    PaymentMethodToken = Request.Query.token,
                    RedirectUrl = ConfigurationManager.AppSettings["PublicWebUrl"] + "/3d-secure/redirect-after",
                    CallbackUrl = ConfigurationManager.AppSettings["PublicWebUrl"] + "/3d-secure/callback"
                });

                if (transaction.State == "pending" && !string.IsNullOrWhiteSpace(transaction.CheckoutUrl))
                {
                    return Response.AsRedirect(transaction.RedirectUrl);
                }

                if (transaction.State == "pending" && !string.IsNullOrWhiteSpace(transaction.CheckoutForm))
                {
                    return View["Transaction3DSecureForm", transaction.CheckoutForm];
                }

                if (transaction.Succeeded)
                {
                    return View["Success"];
                }

                var viewModel = new TransactionViewModel();

                viewModel.PopulateFromTransaction(transaction, ConfigurationManager.AppSettings["PublicWebUrl"] + "/3d-secure/redirect", service.APIEnvironment);

                return View["TakePayment", viewModel];
            };

            // Redirect after 3d secure
            Get["/redirect-after"] = parameters =>
            {
                Transaction transaction = service.GetTransaction(Request.Query.transaction_token);

                if (transaction.Succeeded)
                {
                    return View["Success"];
                }

                var viewModel = new TransactionViewModel();

                viewModel.PopulateFromTransaction(transaction, ConfigurationManager.AppSettings["PublicWebUrl"] + "/3d-secure/redirect", service.APIEnvironment);

                return View["TakePayment", viewModel];
            };

            // Callback after 3d secure, happens if something goes wrong/cancels also
            Post["/callback"] = parameters =>
            {
                var xmlBody = new StreamReader(Request.Body).ReadToEnd();

                var transactions = service.DeserializeTransactions(xmlBody).ToList();

                if (!transactions.Any())
                    return "Pingback";

                foreach (var transaction in transactions)
                {
                    if (service.ValidateTransactionSignature(transaction))
                    {
                        var token = transaction.Token;

                        // Do stuff in your database
                    }
                    else
                    {
                        var token = transaction.Token;

                        // Perhaps log we have an invalid transaction
                    }
                }

                return "Pingback";
            };
        }