SpringSecurity对CSRF的支持实践

news2024/9/25 9:28:05

【1】什么是CSRF

跨站请求伪造(英语:Cross-site request forgery),也被称为 one-click attack 或者 session riding,通常缩写为 CSRF 或者 XSRF, 是一种挟制用户在当前已登录的Web应用程序上执行非本意的操作的攻击方法。跟跨网站脚本(XSS)相比,XSS利用的是用户对指定网站的信任,CSRF 利用的是网站对用户网页浏览器的信任。

跨站请求攻击,简单地说,是攻击者通过一些技术手段欺骗用户的浏览器去访问一个自己曾经认证过的网站并运行一些操作(如发邮件,发消息,甚至财产操作如转账和购买商品)。由于浏览器曾经认证过,所以被访问的网站会认为是真正的用户操作而去运行。这利用了web中用户身份验证的一个漏洞:简单的身份验证只能保证请求发自某个用户的浏览器,却不能保证请求本身是用户自愿发出的。

从Spring Security 4.0开始,默认情况下会启用CSRF保护,以防止CSRF攻击应用程序,Spring Security CSRF会针对PATCH,POST,PUT和DELETE方法进行防护。

如下所示,默认开启CSRF保护,当发起post请求时会被拦截:

在这里插入图片描述

【2】核心原理

如下所示,在CsrfFilter中会根据请求尝试获取csrfToken。如果不存在,则生成并存储到session和request中。

在这里插入图片描述

这里tokenRepository默认是LazyCsrfTokenRepository包装了HttpSessionCsrfTokenRepository

在这里插入图片描述

默认使用对其请求方式进行判断,如果不是"GET", "HEAD", "TRACE", "OPTIONS"直接放行。

if (!this.requireCsrfProtectionMatcher.matches(request)) {
	filterChain.doFilter(request, response);
	return;
}

然后根据上面得到的csrfToken与请求携带的token进行对比:

//从请求头获取
String actualToken = request.getHeader(csrfToken.getHeaderName());
if (actualToken == null) {
	//从请求参数获取
	actualToken = request.getParameter(csrfToken.getParameterName());
}
//如果token不相等
if (!csrfToken.getToken().equals(actualToken)) {
	if (this.logger.isDebugEnabled()) {
		this.logger.debug("Invalid CSRF token found for "
				+ UrlUtils.buildFullRequestUrl(request));
	}
	//缺失token
	if (missingToken) {
		this.accessDeniedHandler.handle(request, response,
				new MissingCsrfTokenException(actualToken));
	}
	else {
	// token不匹配
		this.accessDeniedHandler.handle(request, response,
				new InvalidCsrfTokenException(csrfToken, actualToken));
	}
	return;
}

【3】应用实践

这里以thymeleaf模板引擎为例说明使用。

① 引入pom文件

<dependency>
    <groupId>org.springframework.boot</groupId>
    <artifactId>spring-boot-starter-thymeleaf</artifactId>
</dependency>
<!--对Thymeleaf添加Spring Security标签支持-->
<dependency>
    <groupId>org.thymeleaf.extras</groupId>
    <artifactId>thymeleaf-extras-springsecurity5</artifactId>
</dependency>

<dependency>
    <groupId>org.springframework.boot</groupId>
    <artifactId>spring-boot-starter-security</artifactId>
</dependency>
<dependency>
    <groupId>org.springframework.boot</groupId>
    <artifactId>spring-boot-starter-web</artifactId>
</dependency>

② 页面携带CSRF信息

<form  method="post" action="update_token">
  <input type="hidden" th:name="${_csrf.parameterName}" th:value="${_csrf.token}"/>
    用户名: <input type="text" name="username" /><br />&nbsp;&nbsp;码: <input type="password" name="password" /><br />
    <button type="submit">修改</button>
</form>

SecurityConfig默认就开启csrf保护功能,无需额外配置。

③ 使用CookieCsrfTokenRepository

其本质是将token持久化在cookie名字为XSRF-TOKEN上,然后从请求头X-XSRF-TOKEN读取进行对比。

如下所示将token包装为cookie对象添加到response上:

@Override
public void saveToken(CsrfToken token, HttpServletRequest request,
		HttpServletResponse response) {
	String tokenValue = token == null ? "" : token.getToken();
	Cookie cookie = new Cookie(this.cookieName, tokenValue);
	cookie.setSecure(request.isSecure());
	if (this.cookiePath != null && !this.cookiePath.isEmpty()) {
			cookie.setPath(this.cookiePath);
	} else {
			cookie.setPath(this.getRequestContext(request));
	}
	if (token == null) {
		cookie.setMaxAge(0);
	}
	else {
		cookie.setMaxAge(-1);
	}
	cookie.setHttpOnly(cookieHttpOnly);
	if (this.cookieDomain != null && !this.cookieDomain.isEmpty()) {
		cookie.setDomain(this.cookieDomain);
	}

	response.addCookie(cookie);
}

SecurityConfig使用如下代码来指定csrfTokenRepository:

and().csrf().csrfTokenRepository(CookieCsrfTokenRepository.withHttpOnlyFalse());

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/710100.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

chatgpt赋能python:如何用Python计算居民用电量

如何用Python计算居民用电量 介绍 居民用电量是一个重要的经济指标。对于一个家庭来说&#xff0c;如果能够掌握自己的用电量情况&#xff0c;不仅可以控制开支&#xff0c;还可以提高用电效率&#xff0c;节约能源。而对于电力公司来说&#xff0c;了解居民用电量的变化规律…

vue 实现色板功能

效果&#xff1a; 动态添加颜色 随机色 代码&#xff1a; <divclass"mt-10 firstTitle"v-show"pictureType ! card && pictureType ! table && pictureType ! inventory"><i:class"[colorSystemShow ? el-icon-com-xia…

关于antd的form表单组件的一个天坑。。。

事情是这样的&#xff0c;项目中遇到了一个问题&#xff0c;用表单包裹着着一个Switch组件&#xff0c;提交表单的时候可以将Switch的值一起提交。 form.setFieldsValue({power:0})<Form.Item label"Switch" name"power"><Switch checked{flag}…

autodl算力租用平台应用于pycharm

一、GPU租用选择 1、创建实例 首先进入算力市场 博客以2080为例&#xff0c;选择计费方式&#xff0c;选择合适的主机&#xff0c;选择要创建实例中的GPU数量&#xff0c;选择镜像&#xff08;内置了不同的深度学习框架&#xff09;&#xff0c;最后创建即可 2、SSH远程连…

第五章 linux编译器——gcc/g++的使用

第五章 linux编译器——gcc/g的使用 一、编辑器与编译器的区别二、gcc/g的编译过程前言1、阶段1&#xff1a;预处理&#xff08;头文件、宏的替换&#xff09;&#xff08;1&#xff09;作用&#xff08;2&#xff09;指令&#xff08;3&#xff09;示例 2、阶段2&#xff1a;编…

Linux--用户身份切换: su

①普通用户切换成超级用户且更改路径&#xff1a;su - ②普通用户切换成超级用户且不更改路径&#xff1a;su root 或者 su ③(由普通用户切换来的)超级用户切换回普通用户&#xff1a;Ctrld ④超级用户切换成普通用户&#xff1a;su 普通用户名 ⑤普通用户a切换成普通用户b…

Jetson Nano Swap交换空间增加

依次输入以下命令&#xff0c;可以使交换空间增加3G&#xff0c;解决一些耗尽内存的程序出错。 sudo fallocate -l 3G /var/swapfile sudo chmod 600 /var/swapfile sudo mkswap /var/swapfile sudo swapon /var/swapfile sudo bash -c echo "/var/swapfile swap swap de…

金九银十1060+ 道 Java面试题及答案整理(2023最新版)

前言 今年的金三银四可是被裁员疫情搞得人心慌慌&#xff0c;由于大厂纷纷裁员&#xff0c;面试的竞争难度又上一层&#xff0c;不知道你是否在金三银四中拿到 offer&#xff1f;不过这些都过去了&#xff0c;现在马上迎来的是金九银十&#xff0c;按照往年来说&#xff0c;秋…

python | 识别项目中的接口并生成接口文档

识别项目中的接口并生成接口文档 前言起点用途使用方法控制台展示文档内容展示代码注意事项 前言 前段时间也是来了一场说走就走的旅行&#xff0c;去看了看祖国的大好河山&#xff0c;不得不说也是一场让我难忘的旅行&#xff0c;可惜钱包太扁了&#xff0c;禁不起我的的折腾…

NOSQL之redis配置和安装

关系数据库与非关系型数据库 ●关系型数据库&#xff1a; 关系型数据库是一个结构化的数据库&#xff0c;创建在关系模型&#xff08;二维表格模型&#xff09;基础上&#xff0c;一般面向于记录。 SQL 语句&#xff08;标准数据查询语言&#xff09;就是一种基于关系型数据库…

Andriod Studio安装使用中

暑假快乐啊&#xff0c;终于考完啦 Android studio安装的前提是必须保证安装了jdk1.8版本以上 如果没有安装好&#xff0c;那么可以参考这个&#xff1a;win10下载jdk18以及环境配置 一、在官网下载Android Studio 官网&#xff1a;https://developer.android.google.cn/stud…

jedis使用,操作Redis数据库1

使用jedis的原因; 1.提高性能&#xff0c;减少Socket的创建和销毁对性能的影响 2.是一个线程安全的网络连接池。可以用JedisPool创建一些可靠Jedis实例&#xff0c;可以从池中获取Jedis实例&#xff0c;使用完后再把Jedis实例归还给JedisPool连接池。合理的JedisPool资源池参数…

8 款在线 API 接口文档管理工具;好用!

1、Postman Postman是被大家所熟知的网页调试Chrome插件&#xff0c;我们常常用它来进行临时的http请求调试。幸运的是&#xff0c;Postman可以将调试过的请求保存到Collection中。形成的Collection就可以作为一份简单有效且支持在线测试的接口文档&#xff0c;使用同一账号登录…

Jenkins+Docker 实现一键自动化部署项目

1、环境配置 环境&#xff1a;centos7git(gitee) 简述实现步骤&#xff1a;在docker安装jenkins&#xff0c;配置jenkins基本信息&#xff0c;利用Dockerfile和shell脚本实现项目自动拉取打包并运行。 2、安装docker docker 安装社区版本CE 确保 yum 包更新到最新。 yum …

react-redux(由浅到深)

文章目录 1. redux1.1 概述与使用原则1.2工作流程1.2.1 三个核心 1.3 store1.4 action1.5 reducer1.5.1 合并reducers 1.6 dispatch getState 及状态更新 2. react-redux2.1 基本特征2.2 connect()、mapStateToProps2.3 mapDispatchToProps2.4Provider2.5. 中间件&#xff0c;c…

【动手学习深度学习--逐行代码解析合集】04softmax回归的从零开始实现

【动手学习深度学习】逐行代码解析合集 04softmax回归的从零开始实现 视频链接&#xff1a;动手学习深度学习–softmax回归的从零开始实现 课程主页&#xff1a;https://courses.d2l.ai/zh-v2/ 教材&#xff1a;https://zh-v2.d2l.ai/ 1、 softmax网络架构 2、 softmax运算 3、…

实验三:运算类编程实验

实验目的 阐明本实验的目的。 一实验目的掌握学精变C6应) 乘汉运第《结购 3位)江程产设计方法穿握双精度[3位)加法运算乡饰程产设计方法穿握双精度园) 朱讼运算 [结果为64位)汇编往广设计方讯 实验要求 说明实现本实验需要掌握的知识及本实验需要的实验环境 、实强要求 了解简单…

20+个小而精的Python实战案例(附源码和数据)

公众号&#xff1a;尤而小屋作者&#xff1a;Peter编辑&#xff1a;Peter 大家好&#xff0c;我是Peter~ 最近小编认真整理了20个基于python的实战案例&#xff0c;主要包含&#xff1a;数据分析、可视化、机器学习/深度学习、时序预测等&#xff0c;案例的主要特点&#xff1…

spring boot security验证码登录示例

前言 在spring boot security自定义认证一文&#xff0c;基本给出了一个完整的自定义的用户登录认证的示例&#xff0c;但是未涉及到验证的使用&#xff0c;本文介绍登录的时候如何使用验证码。 本文介绍一个验证码生成工具&#xff0c;比较老的一个库了&#xff0c;仅作demo…

rust warp框架教程1-helloworld

warp框架简介 warp is a super-easy, composable, web server framework for warp speeds. warp建立在hyper之上&#xff0c;因此&#xff0c;warp天生支持异步&#xff0c;HTTP/2&#xff0c;以及“正确的HTTP实现”。 warp的强大之处在于其提供的filter系统&#xff0c;它…