springsecurity

SpringSecurity应用场景

1. 用户登录, 传统基于web开发的项目的登录功能
2. 用户授权, 在系统中用户拥有哪些操作权限
3. 单一登录, 一个账号只能在同一时间只能在一个地方进行登录, 如果在其他地方进行第二次登录,则剔除之前登录操作
4. 集成cas,做单点登录,即多个系统只需登录一次,无需重复登录
5. 集成oauth2 ,做登录授权, 可以用于app登录和第三方登录(QQ,微信等), 也可以实现cas的功能

Spring Security依赖包功能的实现主要是由一系列过滤器相互配合完成。也称之为过滤器链(按以下顺序去执行)(下面的filter都来自 spring.security.web这个包下)

1.org.springframework.security.web.context.request.async.WebAsyncManagerIntegrationFilter
	根据请求封装获取WebAsyncManager,从WebAsyncManager获取/注册的安全上下文可调用处理拦截器

2.org.springframework.security.web.context.SecurityContextPersistenceFilter
	SecurityContextPersistenceFilter主要是使用SecurityContextRepository在session中保存
	或更新一个SecurityContext,并将SecurityContext给以后的过滤器使用,来为后续fifilter
	建立所需的上下文。SecurityContext中存储了当前用户的认证以及权限信息。
	
3.org.springframework.security.web.header.HeaderWriterFilter
	向请求的Header中添加相应的信息,可在http标签内部使用security:headers来控制
	
4.org.springframework.security.web.csrf.CsrfFilter
	csrf又称跨域请求伪造,SpringSecurity会对所有post请求验证是否包含系统生成的csrf的
	token信息,如果不包含,则报错。起到防止csrf攻击的效果。
	
5.org.springframework.security.web.authentication.logout.LogoutFilter
	匹配URL为/logout的请求,实现用户退出,清除认证信息。
	
6.org.springframework.security.web.authentication.UsernamePasswordAuthenticationFilter
	表单认证操作全靠这个过滤器,默认匹配URL为/login且必须为POST请求。
	(这个就是 处理 login.html提交的请求的,认证判断的,filter)
	
7.org.springframework.security.web.authentication.ui.DefaultLoginPageGeneratingFilter
	如果没有在配置文件中指定认证页面,则由该过滤器生成一个默认认证页面。
	(这个就是判断是否 login的 filter)
	
8.org.springframework.security.web.authentication.ui.DefaultLogoutPageGeneratingFilter
	由此过滤器可以生产一个默认的退出登录页面
	
9.org.springframework.security.web.authentication.www.BasicAuthenticationFilter
	此过滤器会自动解析HTTP请求中头部名字为Authentication,且以Basic开头的头信息。
	
10.org.springframework.security.web.savedrequest.RequestCacheAwareFilter
	通过HttpSessionRequestCache内部维护了一个RequestCache,用于缓存HttpServletRequest
	
11.org.springframework.security.web.servletapi.SecurityContextHolderAwareRequestFilter
	针对ServletRequest进行了一次包装,使得request具有更加丰富的API
	
12.org.springframework.security.web.authentication.AnonymousAuthenticationFilter
	当SecurityContextHolder中认证信息为空,则会创建一个匿名用户存入到
	SecurityContextHolder中。spring security为了兼容未登录的访问,也走了一套认证流程,只不过是一个匿名的身份

13.org.springframework.security.web.session.SessionManagementFilter
	securityContextRepository限制同一用户开启多个会话的数量
	
14.org.springframework.security.web.access.ExceptionTranslationFilter
	异常转换过滤器位于整个springSecurityFilterChain的后方,用来转换整个链路中出现的异常

15.org.springframework.security.web.access.intercept.FilterSecurityInterceptor
	获取所配置资源访问的授权信息,根据SecurityContextHolder中存储的用户信息来决定其是否有权限
	Spring Security默认加载15个过滤器, 但是随着配置可以增加或者删除一些过滤器.

主要有 三个包 (具体包的源码功能细节,暂时没去了解),然后 springboot的autoconfiguration配置类 去ioc他们

1.spring-security-config
2.spring-security-core
3.spring-security-web

认证方式

1. HttpBasic认证
	 	HttpBasic登录验证模式是Spring Security实现登录验证最简单的一种方式,也可以说是最简陋
	的一种方式。它的目的并不是保障登录验证的绝对安全,而是提供一种“防君子不防小人”的登录验证。

		在使用的Spring Boot早期版本为1.X版本,依赖的Security 4.X版本,那么就无需任何配置,启动
	项目访问则会弹出默认的httpbasic认证。现在使用的是spring boot2.0以上版本(依赖Security
	5.X版本),HttpBasic不再是默认的验证模式,在spring security 5.x默认的验证模式已经是表单模式

		HttpBasic模式要求传输的用户名密码使用Base64模式进行加密。如果用户名是 "admin" ,
	密码是“ admin”,则将字符串"admin:admin" 使用Base64编码算法加密。加密结果可能是:
	YWtaW46YWRtaW4=。HttpBasic模式真的是非常简单又简陋的验证模式,Base64的加密算法是
	可逆的,想要破解并不难

2. formLogin登录认证模式(用的多)
		Spring Security的HttpBasic模式,该模式比较简单,只是进行了通过携带Http的Header进行
	简单的登录验证,而且没有定制的登录页面,所以使用场景比较窄。对于一个完整的应用系统,与
	登录验证相关的页面都是高度定制化的,非常美观而且提供多种登录方式。这就需要Spring
	Security支持我们自己定制登录页面, spring boot2.0以上版本(依赖Security 5.X版本)默认会生
	成一个登录页面.

security的自定义功能 和 mvc web的一样,springboot 会 执行WebMvcAutoConfiguration Adapter 和 WebSecurityConfigurerAdapter 的 一些config方法,所以想要自定义功能,就是注入WebSecurityConfigurerAdapter 的子类,重写方法,这样,就可以执行到 你重写的方法,但是 这不会覆盖springboot原有的方法的执行,只是扩展组件功能

  1. void configure(WebSecurity web)

  2. void configure(HttpSecurity http)

  3. void configure(AuthenticationManagerBuilder auth)

  4. 关于自定义的 configure配置基本就是这 三个方法,对web , http作一些设置,就可以导致后面的功能发生变化因为后面执行的方法,都是会依赖 web,http的

SpringSecurity 中,安全构建器 HttpSecurity 和 WebSecurity 的区别是 :

  1. WebSecurity 不仅通过 HttpSecurity 定义某些请求的安全控制,也通过其他方式定义其他某些请求可以忽略安全控制;

  2. HttpSecurity 仅用于定义需要安全控制的请求(当然 HttpSecurity 也可以指定某些请求不需要安全控制);

  3. 可以认为 HttpSecurity 是 WebSecurity 的一部分, WebSecurity 是包含 HttpSecurity 的更大的一个概念;

  4. 构建目标不同
    WebSecurity 构建目标是整个 Spring Security 安全过滤器 FilterChainProxy`,
    HttpSecurity 的构建目标仅仅是 FilterChainProxy 中的一个 SecurityFilterChain 。

  5. 简单来说,webSecurity的控制范围更大,httpSecurity有的功能,webSecurity都有,一般可以用 webSecurity来控制哪些请求可以放行,用httpSecurity来控制,哪些请求必须走过滤器

安全构建器的类结构分析

public final class HttpSecurity 
		extends
		AbstractConfiguredSecurityBuilder<DefaultSecurityFilterChain, HttpSecurity>
		implements 
		SecurityBuilder<DefaultSecurityFilterChain>,
		HttpSecurityBuilder<HttpSecurity> 
public final class WebSecurity 
		extends
		AbstractConfiguredSecurityBuilder<Filter, WebSecurity> 
		implements
		SecurityBuilder<Filter>, ApplicationContextAware 

主要继承和实现的就是
AbstractConfiguredSecurityBuilder
SecurityBuilder

以httpSecurity为例,分析下里面的方法

  1. 一般我们想用 http构建某个功能板块的自定义设置的时候,一般调用的就是 xxx() 会返回一个 xxxConfigurer < HttpSecurity > ,通过这个 configurer去设置 自定义设置,xxxConfiguration的方法都是采用的 链式调用 会返回 xxxConfiguration,然后设置完了后,调用 and(),会 返回 http ,xxxConfiguration 都是 底层继承了 SecurityConfigurerAdapter,里面有and()方法,会返回 http

  2. 当某个功能设置完成,调用 xxxConfiguraiton的 and() 方法,返回 http,然后 又可以拿着这 http 去获得其他的 xxxConfiguration功能模块的设置

  3. 总之就2点:1.链式调用 ,2.http去获得 xxxConfiguration去完成功能的设置

springSecurity都是 filter来处理 认证和授权

例如,我们如果写一个 filter来认证,那么没有登入的话,就会去login.html页面,而 action就是我们处理 认证判断的地方,认证成功就会,去往认证成功的 页面(例如 index.html),但是,在springSecurity里面,他已经写好了 认证的地方,在login.html 的 action不管是啥,都会去 处理 认证判断的地方,只是 在 security里面,处理 认证判断的 不是某个接口,而是 UsernamePasswordAuthenticationFilter 这个filter,而这个filter 正好拦截的 就是 我们 http.formLogin()// 开启表单认证
.loginProcessingUrl(“/login”)//表单提交的路径 在这里配置后,当然 login.html的action要和 配置类中配置的 一样,这样 login.html提交后,就会 发 /login请求,被 UsernamePasswordAuthenticationFilter拦截,处理认证 判断,认证成功,就直接 跳转成功页面(也是在 配置类中配置),失败,就会重定向到 login.html页面(也是在配置类中配置)

简单来说,springSecurity将 认证 和 授权的 处理都写好了(都是 filter),而不是某个具体的接口,而怎么样到这个 处理方法,普通的方法是 提供接口,然后filter 跳转或重定向到这个接口地址,而 springSecurity 就直接 提供 filter来处理认证判断,而不是接口,但是也是提供url,只是 具体的filter 拦截 具体的 url,直接就在 filter处理了 认证和授权了,而不是专门提供接口处理

所以,只要搞清楚 15个 filter 各自拦截哪些 url,以及这 15个 filter的具体功能,是判断是否登入,还是用来处理login.html提交的 认证请求,等等就可以 完成认证和授权功能,然后就是通过 configue() 方法,来 协助 这 15个 filter 完成自己功能,因为这 15个 filter 都会 从 httpSecurity系列对象,中 去动态的 读取 filter所需要的信息(例如,拦截哪些请求,认证成功跳转的地址,表单提交的路径 等等)

表单登录的具体过程

  1. UsernamePasswordAuthenticationFilter是 login.html 提交的表单请求的

  2. 注意 userfilter 获得 提交的 action username,password的 name定义,是 通过 http设置的configuration 动态获得

    所以,http里面设置的loginAction,usernameParameter(“”).passwordParameter(“”)
    必须 要和 login.html提交的 一致才行,这样 动态获得的 action,username,password的自定义名字,filter 在 通过 req.getParamter(“configuration的自定义 name”)获得的时候,才能取到数据

在这里插入图片描述

  1. 在源码中可以观察到, 表单中的input的name值是username和password, 并且表单提交的路 径为 /login , 表单提交方式method为 post , 这些可以修改为自定义的值.
    但是 自定义的值,必须与 表单的 对于的 inputname,action 一样才行

  2. 然后 UsernamePasswordAuthenticationFilter的 认证方法,会简单的 判断认证是否成功,成功后重定向 指定的successForwardUrl , 失败就会 重定向到 loginPage(“/toLoginPage”)// 自定义登录页面

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值