通过修改cookie完成攻击漏洞及jwt修复

77 阅读2分钟

攻击面

1.使请求拦截工具(Charles等)处于打开状态

2.使用管理员账户登录应用程序。

3.在账号列表的搜索框中输入普通用户,查询普通用户信息。

4.选择用户搜索结果部分中的普通用户 链接。

5.检查拦截的请求并查看 cookie 包含loggedIn、role 和 jwt 值。提交请求并注意可以看到 普通用户 的帐户信息。角色现在的值为Administrator

6.使用普通用户 登录应用程序。

7.在搜索框中输入管理员,然后选择“搜索”按钮。

8.检查拦截的请求并查看角色和 jwt 的值已更改:角色现在的值为User

9.从 cookie 复制 jwt 值并在 jwt.io 对其进行解码,以确认有效负载中的角色属性也具有“User”值。

10.尝试通过单击 管理员 链接来查看 管理员 的帐户,并确认您收到“访问被拒绝:需要管理员访问”错误消息。

11.返回搜索页面并再次搜索管理员。这次,点击管理员链接后,通过将cookie更改为role=Administrator来利用该漏洞;而不是角色=用户;并验证您现在是否能够看到 管理员 的帐户信息。

修复

1.打开服务端代码 2.通过从解码的 JWT(而不是 cookie)中提取角色来修复漏洞。 修改前

def account_lookup(session):
    user_id = session["user_id"]
    cookies = session["cookies"]
    decoded_jwt = session["decoded_jwt"]

    username = decoded_jwt["username"]
    current_users_id = get_user_id(username)

    if not user_exists(username):
        raise Exception("Bad Request")

    if int(current_users_id) == int(user_id):
        return get_account(user_id)

    if not cookies.get("role") == "Administrator":
        raise Exception("Access Denied: Administrator Access Required")

    return get_account(user_id)

修改后

def account_lookup(session):
    user_id = session["user_id"]
    cookies = session["cookies"]
    decoded_jwt = session["decoded_jwt"]

    username = decoded_jwt["username"]
    current_users_id = get_user_id(username)

    if not user_exists(username):
        raise Exception("Bad Request")

    if int(current_users_id) == int(user_id):
        return get_account(user_id)

    if not decoded_jwt["role"] == "Administrator":
        raise Exception("Access Denied: Administrator Access Required")

    return get_account(user_id)