木易Young 发表于 2024-3-22 16:39

Github 2FA TOTP验证程序

## 1. 背景

2FA即双因素认证(Two-factor authentication),在进行风险操作时,不仅要求密码,还要通过一次性密码(One Time Password)验证通过之后才可以进行操作。
Github要求,到2023年底前,所有用户都必须开启双因素认证,否则无法登录。Github采用的是TOTP验证,即基于时间的一次性密码。网站和用户的共享同一个密钥,双方同时进行相同的运算,在一定时间内(通常30秒)将计算出的验证码提交给Github验证。
安全性:

- 暴力破解。运算出的验证码为6位数字,暴力破解将有100万种组合。由于验证方法基于时间,便要求30秒内能进行100万次验证。

- 站方拦截。站方可以设置同一时段(30秒)内的验证码提交次数上限,超过后只能等待下一时段的验证码。

所以基于时间进行验证,在无法拿到密钥的情况下,难以破解TOTP验证方式,其安全性得到一定保障。

## 2. 代码

下面是Python代码实现TOTP验证,运行以前,需要导入模块:

```python
pip install pyotp time -i https://pypi.tuna.tsinghua.edu.cn/simple
```

此处导入时使用了清华大学源,主要是为了提高导入速度。

使用代码时,需要在keys字典中输入网站名称及其密钥,然后运行即可。


``` python
import pyotp
import time
# 创建一个包含网站和密钥的字典
keys = {
    "GitHub1": "X5CTBOMEYE3TXIIS",
    "Github2": "X5CTBOMEYE3TXIIS"
}
# 打印标题和验证码
print("网站\t\t验证码")
# 遍历每个网站,并为每个密钥生成TOTP验证码并打印
for website, key in keys.items():
    # 对网站名称进行截断,确保不超过一定长度
    truncated_website = website[:20] + "..." if len(website) > 20 else website
    totp_obj = pyotp.TOTP(key)
    verification_code = totp_obj.now()
    print(f"{truncated_website}\t{verification_code}")

```

## 3. 密钥的获取

以Github网站为例,进入到2FA验证的界面后,提供了一个二维码如下,扫描结果如下:otpauth://totp/GitHub:evilsophietheking?secret=ECX3VKG4XX2D5V55&issuer=GitHub​,其中secret后面的字符串即是密钥。通过扫码方式可以实现无信息交换的数据传输,更加确保了安全性。

![](https://docs.github.com/assets/cb-31013/mw-1440/images/help/2fa/ghes-3.8-and-higher-2fa-wizard-app-click-code.webp)
页: [1]
查看完整版本: Github 2FA TOTP验证程序