CSRFToken

一、什么是CSRFToken?

  • CSRF全拼为Cross Site Request Forgery,译为跨站请求伪造。
  • CSRF指攻击者盗用了你的身份,以你的名义发送恶意请求。
    包括:以你名义发送邮件,发消息,盗取你的账号,甚至于购买商品,虚拟货币转账…
  • 造成的问题:个人隐私泄露以及财产安全。

二、 CSRF攻击示意图

客户端访问服务器时没有同服务器做安全验证
在这里插入图片描述

三 、防止CSRF攻击

  1. 在客户端向后端请求界面数据的时候,后端会往响应中的 cookie 中设置 csrf_token 的值
  2. 在 Form 表单中添加一个隐藏的的字段,值也是 csrf_token在用户点击提交的时候,会带上这两个值向后台发起请求
  3. 后端接受到请求,以会以下几件事件:
    1.从 cookie中取出 csrf_token
    2.从 表单数据中取出来隐藏的 csrf_token 的值
    3.进行对比
  4. 如果比较之后两值一样,那么代表是正常的请求,如果没取到或者比较不一样,代表不是正常的请求,不执行下一步操作

提示:代码展示:见<< webA >>, << webB >>文件

3.1 手动解决

  • 在cookie增加一个csrf_token
  • 在表单中增加一个csrf_token
  • 校验: 取出cookie和表单中的csrf_token比较如果二者一致那么是正常请求
  • 具体过程,看keynote图解

3.2 CSRFProtect解决csrf

  • 使用流程:
    • 1.安装扩展包
      pip install flask-wtf
    • 2.导入包
      from flask_wtf.csrf import CSRFProtect
    • 3.创建CSRFProtect对象,保护app对象
    • 4.设置SECRET_KEY,便于csrf_token加密
    • 5.需要在表单中设置csrf_token隐藏字段即可

CSRFProtect一旦保护了app之后, 会对’POST’, ‘PUT’, ‘PATCH’, 'DELETE’做校验.

四、代码示例

4.1 后端代码

from flask import Flask, render_template, request
from flask_wtf.csrf import CSRFProtect

app = Flask(__name__)

# 设置密码
app.config["SECRET_KEY"] = "tianwanggaidihu"

# 保护app
CSRFProtect(app)


@app.route('/', methods=["GET", "POST"])
def hello_world():
    # 1.如果是GET请求,直接返回注册页面
    if request.method == "GET":
        return render_template("file16register.html")
    else:
        # 2.如果是POST请求,处理注册业务
        # 2.1获取参数
        username = request.form.get("username")
        password = request.form.get("password")
        repassword = request.form.get("repassword")

        # 2.2校验参数,为空校验
        if not all([username, password, repassword]):
            return "参数填写不全"

        # 2.3两次密码是否一致
        if password != repassword:
            return "两次密码输入不一致"

        # 2.4返回注册成功
        return "恭喜你, 注册成功"

if __name__ == '__main__':
    app.run(debug=True)

4.2 前端代码

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <title>Title</title>
</head>
<body>

<form action="" method="post">
    {# 只要使用了CSRFProtect保护app,那么可以直接使用csrf_token()方法获取csrf_token值 #}
    <input type="hidden" name="csrf_token" value="{{ csrf_token() }}">
    用户名:<input type="text" name="username"><br>
    密码:<input type="password" name="password"><br>
    确认密码:<input type="password" name="repassword"><br>
    <input type="submit" value="注册">
</form>


</body>
</html>

在这里插入图片描述

### PHP中实现和使用CSRF Token 为了有效防御跨站请求伪造(CSRF),在PHP应用程序中引入CSRF Tokens是非常必要的。这些Tokens是一次性的随机字符串,在表单提交或其他HTTP POST操作时附加到请求中,从而验证该请求确实源自合法页面而非第三方恶意站点。 #### 创建唯一的Token并存储于Session 当用户首次访问涉及敏感数据变更的网页时,服务器端应生成一个独一无二的Token,并将其保存至当前用户的session变量中: ```php <?php // 启动会话管理 if (!isset($_SESSION)) { session_start(); } // 如果尚未创建,则初始化新的CSRF token if(!isset($_SESSION['csrf_token'])) { $_SESSION['csrf_token'] = bin2hex(random_bytes(32)); } ?> ``` 此代码片段确保每次新打开页面都会有一个独特的CSRF令牌被分配给特定用户会话[^1]。 #### 将Token嵌入HTML表单 为了让客户端能够随同POST请求一起发送这个Token,需要将它加入到每一个可能受到CSRF影响的数据提交界面中去: ```html <form action="process.php" method="post"> <!-- 隐藏域用于携带CSRF token --> <input type="hidden" name="csrf_token" value="<?php echo htmlspecialchars($_SESSION['csrf_token']); ?>"> <!-- 正常输入框和其他控件 --> </form> ``` 上述方法通过隐藏字段的方式把之前产生的Token传递给了前端浏览器,使得后续任何基于表单的动作都能带上这一重要凭证[^2]。 #### 检查收到的Token有效性 最后一步是在处理POST请求的服务端脚本里校验传回来的Token是否匹配预期值。只有当二者一致时才允许继续执行业务逻辑;反之则拒绝服务或提示错误信息: ```php <?php // 继续保持之前的会话环境 session_start(); // 获取来自表单提交中的CSRF token $submittedToken = isset($_POST['csrf_token']) ? $_POST['csrf_token'] : ''; // 对比已知的安全token与接收到的内容 if ($submittedToken !== $_SESSION['csrf_token']) { die('Invalid or missing CSRF token.'); } else { // 成功验证后的正常流程... } ?> ``` 这种机制可以有效地阻止未经许可的外部实体冒充真实用户发起非法指令,因为它们无法得知有效的CSRF Token是什么样的[^3]。
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值