HMC SHA1 hash - Java выдает хэш, отличный от C #

Это продолжение этого вопроса, но я пытаюсь перенести код C # на Java вместо кода Ruby на C #, как это было случай в соответствующем вопросе. Я пытаюсь проверить, что зашифрованная подпись , возвращенная из api Recurly.js, действительна. К сожалению, в Recurly нет библиотеки Java, которая могла бы помочь с проверкой подлинности, поэтому я должен реализовать проверку подписи самостоятельно.

Согласно связанному выше вопросу ( this ) следующий код C # может создать хэш, необходимый для проверки подписи, возвращаемой из Recurly:

var privateKey = Configuration.RecurlySection.Current.PrivateKey;
var hashedKey = SHA1.Create().ComputeHash(Encoding.UTF8.GetBytes(privateKey));
var hmac = new HMACSHA1(hashedKey);
var hash = hmac.ComputeHash(Encoding.ASCII.GetBytes(dataToProtect));
return BitConverter.ToString(hash).Replace("-", "").ToLower();

Recurly предоставляет следующие данные в качестве примера для своей подписи страница документации:

незашифрованное проверочное сообщение : [1312701386, transactioncreate, [account_code: ABC, amount_in_cents: 5000, currency: USD]]

закрытый ключ : 0123456789ABCDEF0123456789ABCDEF

итоговая подпись : 0f5630424b32402ec03800e977cd7a8b13dbd153-1312701386

Вот моя реализация Java:

String unencryptedMessage = "[1312701386,transactioncreate,[account_code:ABC,amount_in_cents:5000,currency:USD]]";
String privateKey = "0123456789ABCDEF0123456789ABCDEF";
String encryptedMessage = getHMACSHA1(unencryptedMessage, getSHA1(privateKey));

private static byte[] getSHA1(String source) throws NoSuchAlgorithmException, UnsupportedEncodingException{
    MessageDigest md = MessageDigest.getInstance("SHA-1");
    byte[] bytes = md.digest(source.getBytes("UTF-8"));
    return bytes;
}

private static String getHMACSHA1(String baseString, byte[] keyBytes) throws GeneralSecurityException, UnsupportedEncodingException {
    SecretKey secretKey = new SecretKeySpec(keyBytes, "HmacSHA1");
    Mac mac = Mac.getInstance("HmacSHA1");
    mac.init(secretKey);
    byte[] bytes = baseString.getBytes("ASCII");
    return Hex.encodeHexString(mac.doFinal(bytes));
}

Однако, когда я распечатываю переменную encryptedMessage, она не соответствует части сообщения в примере подписи. В частности, я получаю значение «c8a9188dcf85d1378976729e50f1de5093fabb78» вместо «0f5630424b32402ec03800e977cd7a8b13dbd153».

Обновление

Per @ M.Babcock, я переписал код C # с данными примера, и он вернул тот же результат, что и код Java. Похоже, мой подход к хешированию правильный, но я передаю неправильные данные (unencryptedMessage). Вздох. Я обновлю этот пост, если / когда я смогу определить, какие данные нужно зашифровать, поскольку в «незашифрованном проверочном сообщении», представленном в документации Recurly, кажется, что-то не хватает.

Обновление 2

Оказалось, что ошибка связана с данными / форматом «незашифрованного проверочного сообщения». Сообщение в данных примера на самом деле не зашифровано с предоставленной подписью примера - так что, возможно, это устаревшая документация? Во всяком случае, я подтвердил, что реализация Java будет работать с реальными данными. Спасибо всем.

6
задан Scott Arciszewski 28 May 2019 в 21:05
поделиться