вторник, 26 августа 2014 г.

API Privat24 (Приват24) Пример расчета сигнатуры на C# ASP.NET MVC

Ситуация

Делаю интерфейс к системе онлайн платежей Приват24 (Интернет-эквайринг ПриватБанка)
на ASP.NET MVC (код соответственно на C#)
Документация к системе есть здесь
https://api.privatbank.ua/article/4/

По документации сделал правильную форму для отправки на сервер.

Возникла проблема с разбором ответа

Проблема

Нужно сверить сигнатуру в приватбанковском ответе о платеже.
Но в документации примеры только на PHP.
Решение задачи "в лоб" приводило к неправильной сигнатуре. Пришлось повозиться.
Здесь делюсь результатами.
Примечание: эта статья посвящена только разбору сигнатуры. Остальные вопросы оставил пока за скобками (чтобы не распыляться). Если будет интересно - пишите запросы в комментариях.

Решение

Сначала несколько "помогаторов" (вспомогательные методы)

Помогатор 0

Используем модули

using System;
using System.Collections.Generic;
using System.Globalization;
using System.Linq;
using System.Text;

Помогатор 1

Преобразователь массива байтов в строку

        /// <summary>
        /// Возвращает массив байтов в виде шестнадцатиричной строки
        /// </summary>
        /// <param name="buffer"></param>
        /// <returns></returns>
        private static string GetByteArrayAsHexadecimalString(IEnumerable<byte> buffer)
        {
            return buffer.Select(b => b.ToString("x2")).Aggregate("", (total, cur) => total + cur);
        }


Помогатор 2

Рассчитыватель сигнатуры

        /// <summary>
        /// вычисление сигнатуры приват24
        /// </summary>
        /// <param name="payment"></param>
        /// <param name="password"></param>
        /// <returns></returns>
        private static string ComputeSignature(string payment, string password)
        {
            var str = payment + password;
            var sha1 = System.Security.Cryptography.SHA1.Create();
            var md5 = System.Security.Cryptography.MD5.Create();            

            var md5Res = md5.ComputeHash(Encoding.UTF8.GetBytes(str));
            var md5ResString = GetByteArrayAsHexadecimalString(md5Res);

            var sha1Res = sha1.ComputeHash(Encoding.UTF8.GetBytes(md5ResString));
            var sha1ResString = GetByteArrayAsHexadecimalString(sha1Res);
            return sha1ResString;
        }

Помогатор 3

Превращение полей POST-запроса в словарь (Dictionary<string,string>).
Эту строчку применил в экшене контроллера, чтобы дальше уже работать со словарем, а не с полями формы.

var dic = Request.Form.AllKeys.ToDictionary(key => key, key => Request.Form[key]);

Основной метод

Сверка сигнатуры в ответе системы приват24

        public void ParseResult(Dictionary<string, string> fields)
        {
            var passedsignature = fields["signature"];
            var payment = fields["payment"];
            var computedsignature = ComputeSignature(payment, _merchInfo.Password);
            if (passedsignature == computedsignature)
            {
                Console.WriteLine("Bingo!");
                // тут логика разбора ответа
                // ...
            }
            else
            {
                Console.WriteLine("Сигнатуры не совпадают!");
            }                       
        }


5 комментариев:

  1. Этот комментарий был удален автором.

    ОтветитьУдалить
  2. Привет! Сможешь помочь в расчете сигнатуры? Уже несколько суток получаю Invalid Signature, готов рвать волосы и лезть на потолок

    ОтветитьУдалить
  3. Спасибо, дружище! Сохранил мне кучу нервов и времени.

    ОтветитьУдалить
  4. Здравствуйте, помогите, пожалуйста, с расчетом сигнатуры.

    ОтветитьУдалить