【发布时间】:2020-04-30 17:57:46
【问题描述】:
我正在尝试实现我自己的 PHP 函数来为 Google Authenticator 生成代码。我这样做是为了好玩和学习新东西。这是我所做的:
function twoFactorAuthorizationCode(string $secretBase32, int $digitsCount): string {
$counter = (int) (time() / 30);
$secret = Base32::decode($secretBase32);
$hash = hash_hmac('sha1', $counter, $secret, true); // 20 binary characters
$hexHash = unpack('H*', $hash)[1]; // 40 hex characters
$offset = hexdec($hexHash[-1]); // last 4 bits of $hash
$truncatedHash = hexdec(substr($hexHash, $offset * 2, 8)) & 0x7fffffff; // last 31 bits
$code = $truncatedHash % (10 ** $digitsCount);
return str_pad($code, $digitsCount, '0', STR_PAD_LEFT);
}
我不确定哪一步是错误的,但它不会产生与 Google Authenticator 相同的结果。显然,我尝试使用时间偏移,以防我的时钟与 Google Authenticator 的时钟不同步。
我不确定的一些事情是:
- 应该从 Base32 解码秘密,还是应该保留 Base32 字符串?
- 计数器是 SHA1 哈希的值还是键?
我做了很多实验,但我的算法无法生成有效结果。非常感谢任何建议。
【问题讨论】:
-
你能用spomky-labs/otphp代替自己写吗?
-
我正在努力学习:)
-
@AlexHowansky 我终于知道出了什么问题。如果你有兴趣,请看下面我的回答。
标签: php authorization sha1 one-time-password google-authenticator