首先,不要这样做HASH(DATA + KEY)
。它存在已知的漏洞。这正是HMAC
设计的目的。所以你的哈希是:
hash = HMAC(sha256, data, privateKey)
现在,处理您的问题(如何防止重放攻击)的典型方法是为每个请求添加一个随机因子。有几种方法可以做到这一点,但效果很好的是nonce
基于方法。所以:
nonce = random(16)
now = time()
data = api_data + '|' + nonce + '|' + now
hash = HMAC(sha256, data, privateKey)
apiCall = data '&nonce=' + nonce + '&time=' + now + '&sig=' + hash
然后,在接收方,您跟踪过去 30 秒内看到的随机数列表。如果你得到一个你见过的,然后拒绝 api 调用(因为那将是一个重放攻击)。如果你得到一个超过 30 秒的版本,请拒绝 api 调用。
if (now < time() - 30) {
return false;
} else if (nonceExists(nonce)) {
return false;
}
addNonce(nonce);
data = api_data + '|' + nonce + '|' + now
myhash = HMAC(sha256, data, privateKey)
if (myhash == hash) {
return api_data;
}
return false;
然后您可以每 30 秒(在 cron 作业中)或每周清除 nonce 上的数据库,这并不重要。取决于您的 API 的活跃程度。
不过这里的关键是你想在它们有效时跟踪它们,否则你很容易受到重放攻击......