Как сохранить данные для обработки платежей на странице подтверждения?

Я добавляю страницу подтверждения вашей оплаты в свой новый проект ASP.NET MVC 3. После проверки ввода я затем отображаю страницу подтверждения, чтобы пользователь мог убедиться, что он все ввел правильно. Моя следующая проблема - как сохранить введенные данные, чтобы я мог обработать платеж после того, как они нажмут «Подтвердить». Очевидно, я не хочу создавать скрытые поля с полным номером кредитной карты.

Я использую сеансы для нашей корзины покупок, но шифрует ли это данные, чтобы нельзя было взломать номер кредитной карты? Каков рекомендуемый подход к этому? Поисковые запросы, которые я выполнял в Google, на самом деле не очень популярны.

Я отображаю информацию, которую они ввели на предыдущей странице (для подтверждения ввода данных). Конечно, правильно замаскировать номер кредитной карты.

Платежная информация

Имя на кредитной карте: Имя

Номер кредитной карты: XXXX XXXX XXXX 1111

Срок годности: 10/2011

Код подтверждения карты: 100

Общая сумма: 50,86 долларов США.

Все цифры в этом посте, конечно же, фальшивые.

Вот код, который я использую до сих пор.

    //
    // POST: /Checkout/AddressAndPayment
    [HttpPost]
    public ActionResult AddressAndPayment(Cart cart, PaymentForm formData)
    {
        if (cart.Items.Count() == 0)
        {
            ModelState.AddModelError("", "Sorry your cart is empty!");
        }

        if (ModelState.IsValid)
        {
            var viewModel = new AddressPaymentViewModel
            {
                FormData = formData,
                Cart = cart
            };

            return View("Confirm", viewModel);
        }
        else
        {
            var viewModel = new AddressPaymentViewModel
            {
                FormData = formData,
                Cart = cart,
                States = States.GetStatesDDL(),
                CreditCardTypes = CreditCartTypes.GetCreditCardTypesDDL()
            };
            return View(viewModel);
        }
    }

    //
    // GET: /Checkout/Confirm
    public ViewResult Confirm()
    {
        return View();
    }

Итак, оттуда, когда я бегу

    //
    // POST: /Checkout/Confirm
    [HttpPost]
    public ViewResult Confirm(Cart cart, PaymentForm formData)
    {
        return View();
    }

Мне все еще нужны данные формы для отправки обработчику кредитной карты.

Есть лучший способ сделать это? Какая лучшая практика?

Другой метод у меня есть видно, как выполнить PreAuth и PostAuth с процессором кредитной карты и не хранить этот период данных, а только идентификатор заказа.


person Mike Wills    schedule 28.09.2011    source источник
comment
Лучшая практика - позволить кому-то, кто знает, что он делает, заниматься платежом, вы отправляете ему пользователя с информацией о клиенте и заказе, а затем возвращаетесь вам для подтверждения. Это также сэкономит вам десятки тысяч долларов на сверхзащищенную инфраструктуру и аудит.   -  person cjk    schedule 29.09.2011


Ответы (4)


После изучения наших вариантов. Мы решили провести транзакцию предварительной авторизации. Таким образом, все, что нам нужно сохранить, это идентификатор заказа, полученный от обработчика, а затем, после подтверждения деталей, мы отправим транзакцию авторизации публикации для фактической публикации платежа.

person Mike Wills    schedule 29.09.2011

На самом деле не показывайте номер кредитной карты на этой странице. Просто покажите последние четыре цифры, чтобы они могли убедиться, что используют правильную кредитную карту.

Я знаю, что вы, вероятно, захотите отобразить его, чтобы убедиться, что они не ввели его неправильно. Помимо того факта, что немногие пользователи когда-либо дважды проверяют весь номер кредитной карты, вы можете выявить большинство потенциальных ошибок, проверив номер кредитной карты по Алгоритм Луна. Если номер кредитной карты введен неправильно, шансы на то, что он пройдет мимо алгоритма Луна, очень и очень мала. Затем вы можете попросить их повторно ввести номер карты, прежде чем перейти на страницу сводки.

person John Conde    schedule 28.09.2011
comment
Я добавил, что делаю сейчас (перед этим постом). Но как передать эту информацию следующему действию, которое фактически обработает платеж? - person Mike Wills; 28.09.2011

Вы можете сохранить модель в переменной сеанса перед загрузкой страницы подтверждения. Помните, что переменные сеанса не обязательно являются только переменными, но могут быть целым объектом.

Session["submitted_data"] = util.Encrypt(Model); //Util.Encrypt would be your custom Encryption lib

РЕДАКТИРОВАТЬ

К сожалению, пропущен бит учетных данных CC.

Это немного сложнее. Вы можете запросить учетные данные кредитной карты ПОСЛЕ страницы подтверждения заказа, ЛИБО вы можете создать таблицу Temp_Confirmation в своей базе данных. Оттуда вы зашифруете учетные данные CC, сохраните их в БД до тех пор, пока они не пройдут страницу подтверждения (сохраните GUID таблицы в скрытом поле), и получите его на другом конце. Просто не забудьте зашифровать и расшифровать, а также удалить запись, когда закончите с ней.

person Chase Florell    schedule 28.09.2011
comment
Будет ли работать шифрование объекта в сеансе? Есть ли лучший способ сделать то, что я пытаюсь сделать? - person Mike Wills; 28.09.2011
comment
Я лично его зашифрую и закину в базу. - person Chase Florell; 28.09.2011
comment
Вот некоторое безопасное состояние сеанса - person Chase Florell; 28.09.2011
comment
использовать SHA1 / MD5 / ... или другие схемы одностороннего шифрования, которые делают невозможным обратное проектирование учетных данных из их сохраненного хэша. - person Agnius Vasiliauskas; 29.09.2011
comment
Шифрование номеров CC в базе данных на стороне сервера - плохая идея. Вы сразу попадаете на территорию PCI-DSS. - person PaulG; 29.09.2011
comment
Вот почему я избегаю этого. Смотрите мой ответ о том, что мы планируем делать. - person Mike Wills; 29.09.2011
comment
@PaulG, я предполагаю, что Майк уже имел дело с PCI-DSS, так как он принимает платежи на своем собственном сервере. Однако я думаю, что идея предварительной авторизации - лучший способ обойти мой ответ. - person Chase Florell; 30.09.2011
comment
Да, мы не хотим нигде хранить кредитную карту, поэтому нам не нужно беспокоиться об этих строгих правилах. Хотя мы стараемся следовать им, как если бы мы это делали. - person Mike Wills; 30.09.2011

По идее, вам просто нужно «сохранить» информацию на стороне сервера для последующей обработки. Нет причин отправлять эту информацию обратно клиенту в виде скрытых полей, файлов cookie, параметров или чего-либо еще. Теперь, если вам нужно сохранить его на стороне сервера, у вас есть несколько вариантов:

1) Состояние сеанса - преимущество, теперь оно там, очищается автоматически и (возможно) только для памяти. Недостатки, у вас только один из них за сеанс. С появлением просмотра с вкладками мы обнаружили, что хранить что-либо транзакционное в состоянии сеанса проблематично.

2) Сохранение в БД - преимущество, просто сохранить и легко восстановить. Вы можете получить его в том же сеансе, или в другом сеансе, или даже с другого компьютера, если у вас есть правильные ключи. Недостатки, вы сохраняете информацию, и вам нужно ее очистить.

Я бы выбрал вариант 2. Просто запишите информацию в таблицу, а затем прочтите ее, когда она вам понадобится. Вы, конечно, должны зашифровать CC-номер, но это тривиальная задача.

person Walden Leverich    schedule 28.09.2011
comment
Шифрование номеров карт на стороне сервера - плохая идея. Шифрование - это просто. Ключевого управления нет. К тому же вся тяжесть аудита PCI-DSS ложится на ваши плечи. - person PaulG; 29.09.2011
comment
Ну да, но если вы собираетесь их хранить, вам нужно их зашифровать. В некоторых (многих?) Случаях было бы проще передать проблему стороннему процессору, но это не сработает, поскольку вы попадаете в более крупные организации, которые сами обрабатывают весь процесс. - person Walden Leverich; 27.10.2011