再次将散列数据作为散列键传递会返回错误的结果 [英] Passing hashed data as key to hash again returns incorrect results

查看:92
本文介绍了再次将散列数据作为散列键传递会返回错误的结果的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我正在创建一个脚本,该脚本将使用GAS访问AWS服务.我将Utilities库中的哈希函数用于创建v4签名所需的所有哈希.这些函数似乎能够一次成功地对数据进行哈希处理,但是尝试将哈希数据传递到参数中会产生错误的结果.还有其他人遇到这个问题并解决吗?

I'm creating a script that will access AWS services using GAS. I'm using the hashing functions in the Utilities library for all the hashing that is required to create a v4 signature. These functions appear to be able to successfully hash data once, but trying to pass in hashed data into an argument yields incorrect results. Anyone else run into this issue and figure it out?

我知道 Utilities.computeHmacSha256Signature(input,key)发生了一些奇怪的事情,因为参数只能是字节数组或字符串,并且我将两者的组合作为参数传递.但是,当我尝试将参数转换为字节数组或字符串时,仍然没有运气.

I know there is something weird going on with Utilities.computeHmacSha256Signature( input, key ), because the arguments can only be byte arrays or strings, and I am passing in combinations of the two. However, when I try to convert the arguments to just byte arrays or strings, I still have no luck.

我的密钥生成代码 设计参考:链接

function getSignatureKey( key, dateStamp, regionName, serviceName ) {
  var kSecret = 'AWS4' + key;
  var kDate    = hash( dateStamp, kSecret );
  var kRegion  = hash( regionName,  kDate );
  var kService = hash( serviceName, kRegion );
  var kSigning = hash( 'aws4_request', kService );
  return kSigning;
}

我的"哈希功能:

function hash( payload, key ) {
  const utf8 = Utilities.Charset.UTF_8;
  const sha256 = Utilities.DigestAlgorithm.SHA_256;
  if ( !payload ) payload = '';

  if ( key ) {
    payload = Utilities.computeHmacSha256Signature( payload, key, utf8 );
  }
  else
    payload = Utilities.computeDigest( sha256, payload, utf8 );

  return  payload;
}

示例输入

var key     = 'wJalrXUtnFEMI/K7MDENG+bPxRfiCYEXAMPLEKEY';
var date    = '20150830';
var region  = 'us-east-1';
var service = 'iam';

根据示例输入生成的密钥 来自链接

c4afb1cc5771d871763a393e44b703571b55cc28424d1a5e86da6ed3c154a4b9

分步结果 jsSHA

// kDate = HMAC( date, 'AWS4' + key )
0138c7a6cbd60aa727b2f653a522567439dfb9f3e72b21f9b25941a42f04a7cd

// kRegion = HMAC( region, kDate )
f33d5808504bf34812e5fade63308b424b244c59189be2a591dd2282c7cb563f

// kService = HMAC( service, kRegion )
199e1f48c602a5ae77ce26a46906920e76fc8427aeaa53da643646fcda1ccfb0

// kSigning = HMAC( 'aws4_request', kService ) -- matches example
c4afb1cc5771d871763a393e44b703571b55cc28424d1a5e86da6ed3c154a4b9

我的结果 运行上面的hash()函数的结果(通过十六进制编码器)

// var kSecret = 'AWS4' + key;
// var kDate    = hash( dateStamp, kSecret )
0138c7a6cbd60aa727b2f653a522567439dfb9f3e72b21f9b25941a42f04a7cd

// var kRegion  = hash( regionName,  kDate );
67a1e58cdd80d4ae0eab4345f1cac6e4faab10efb9c21fd7b30e5e9118462c79

// var kService = hash( serviceName, kRegion );
295384288c76cdb665c1cbf8281250b93b6ae257b98b72e4be0876a9e8a0b409

// var kSigning = hash( 'aws4_request', kService );
bfb393756c5518b668b5055910bb715e4a879c0e10bb22d3140b1e82b2a50a2c

推荐答案

此修改如何?

Utilities.computeHmacSha256Signature(value, key)valuekey均为字符串"或字节[]".在脚本中,运行var kDate = hash( dateStamp, kSecret );时,kDate是字节数组.但是,当运行var kRegion = hash( regionName, kDate );时,regionNamekDate分别是"String"和"Byte []".这样,在var kRegion = hash( regionName, kDate );之后,结果与jsSHA的结果不同.

Both value and key of Utilities.computeHmacSha256Signature(value, key) are "String" or "Byte[]". In your script, when var kDate = hash( dateStamp, kSecret ); is run, kDate is the byte array. But when var kRegion = hash( regionName, kDate ); is run, regionName and kDate are "String" and "Byte[]", respectively. By this, after var kRegion = hash( regionName, kDate );, the result is not the same with that of jsSHA.

  • 例如,为了避免这种情况,请将"String"转换为"Byte []".
function sample() {
  var key = 'wJalrXUtnFEMI/K7MDENG+bPxRfiCYEXAMPLEKEY';
  var dateStamp = '20150830';
  var regionName = 'us-east-1';
  var serviceName = 'iam';
  var kSecret = 'AWS4' + key;

  regionName = Utilities.newBlob(regionName).getBytes(); // Added
  serviceName = Utilities.newBlob(serviceName).getBytes(); // Added
  var value = Utilities.newBlob('aws4_request').getBytes(); // Added

  var kDate    = hash( dateStamp, kSecret );
  var kRegion  = hash( regionName,  kDate );
  var kService = hash( serviceName, kRegion );
  var kSigning = hash( value, kService );
  return kSigning;
}

function hash( payload, key ) {
  return Utilities.computeHmacSha256Signature(payload, key);
  // return Utilities.computeHmacSignature(Utilities.MacAlgorithm.HMAC_SHA_256, payload, key) // You can also use this.
}

结果:

kDate: 0138c7a6cbd60aa727b2f653a522567439dfb9f3e72b21f9b25941a42f04a7cd
kRegion: f33d5808504bf34812e5fade63308b424b244c59189be2a591dd2282c7cb563f
kService: 199e1f48c602a5ae77ce26a46906920e76fc8427aeaa53da643646fcda1ccfb0
kSigning: c4afb1cc5771d871763a393e44b703571b55cc28424d1a5e86da6ed3c154a4b9

参考文献:

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆