个人主页: 【⭐️个人主页】
需要您的【 点赞+关注】支持
本文核心知识点:
spring boot & security
version : 3.1.5
权限系统分为两部分
认证
是指确认声明者的身份
。对应英文 identification
单词。
常见的认证方式:
- 身份证
- 用户名和密码
- 手机:手机短息、二维码扫描、手势密码
- 电子邮箱
- 用户的生物学特征:指纹、虹膜
- 等等
指获取用户的委派权限
。对应英文 authorization
单词。
在信息安全领域,授权
是指资源所有者
委派执行者
,赋予执行者指定范围的资源操作权限
。
资源所有者
和执行者
不限于自然人,很多时候是应用程序或者机器,例如浏览器。
授权的实现方式很广泛,在互联网应用开发领域中:
- 通过 web 服务器的 session 机制
- 通过 web 服务器的 cookie 机制
- 颁发授权令牌 token
鉴权
是指对于一个声明者所声明的身份权利的真实性进行鉴别确认的过程。对应英文 authentication
单词。
先授权
,后鉴权
。这两个“权
”是同一个概念,就是所委派的权利
。
因此鉴权的实现方式和授权的方式有一一对应关系
。
鉴权是一个承上启下
的一个环节,上游它接受权限的输出,校验其真实性后,然后获取权限(permission),为下一步的权限控制
做好准备。
权限控制
是指对可执行的各种操作组合配置
为权限列表
,然后根据执行者的权限
,若其操作在权限范围内,则允许执行,否则禁止。对应英文 access/permission control
单词。
权限
(Permission),一般预先定义和配置好,以便控制的具体实现。一班情况下,会用基于角色的方式来定义权限,由角色来封装可执行的操作集合。
这四个环节是一个前后依次发上、上下游的关系。
认证 ->
授权
-> 鉴权
-> 权限控制
认证
是确认声明者的本身身份
,其作为授权
的上游
衔接而存在
即先登录,后配置权限
鉴权
是对声明者所声明的真实性
进行确认的过程,其作为授权
的下游
衔接而存在
先配置权限,才能鉴别用户的权限和后续的权限控制。
因为HTTP协议的无状态性
,服务器每次访问都需要知道身份才能访问资源。所以每次访问都会发送身份信息进行身份验证。
在访问资源时,直接携带认证身份信息【如账号密码】,通过访问资源时,校验身份。如果身份合法,则可以访问资源
问题
: 每次访问时,都要走一遍身份认证流程。携带身份信息,安全性非常低。
对于为什么需要Session机制和JWT机制,并且有什么区别?推荐大家阅读这篇博文。
身份认证——session认证机制与JWT认证机制(入门到使用)
阅读关注的知识点:
1. Cookie的作用和缺点
2. Session
3. JWT
4. Session和Jwt的区别和选择时机
根据上章讲的3种认证方式如何在spring security对应
直接携带认证令牌访问资源
httpSecurity.formLogin()
// 配置的就是身份认证流程【登录流程】
该方法创建了一个UsernamePasswordAuthenticationFilter
类,用户处理/login
请求的处理。包括认证成功handler和失败handler,以及参数配置,失败跳转。
Session 认证机制
会话管理支持由几个组件组成,它们一起工作以提供该功能。这些组件是: SecurityContextHolderFilter
、 SecurityContextPersistenceFilter
和 SessionManagementFilter
。
在 Spring Security 6 中,SecurityContextPersistenceFilter 和 SessionManagementFilter 默认是不设置的。除此之外,任何应用程序只能设置 SecurityContextHolderFilter 或 SecurityContextPersistenceFilter,而不能同时设置。
spring security 6使用 SecurityContextHolderFilter ,
HttpSessionSecurityContextRepository
, 保存session信息。
写入响应头。
JWT认证流程
spring security 默认没有JWT认证的实现Filter
默认UsernamepassowrdAuthenticationFilter
的用户名密码认证流程,只支持 username和密码。如果我们需要提供额外的字段则无法满足要求。需要我们自定义逻辑。
方式
重写usernamepasswordauthenticationFilter的认证逻辑Filter。注入到原有的的认证filer之前
不好的地方:
1. 原有的usernamefilter 无法移出。并通过httpsecurity.form()进行配置。与自己的 定义的filter 不能同时配置,比较麻烦。
2. 需要对spring security框架比较熟悉。后续开发人员要求高
3. 不同的继承类,不同的效果。一般继承自定义的继承类AbstractAuthenticationProcessingFilter
,对其重写
4. 使用HttpServletRequest和HttpServletResponse类,不能使用Spirng Bean自动转换的能力。增加额外的转换复杂度
禁用原有的认证。通过 提供 controller api的方式暴露身份认证【登录认证】,同时重写 /logout 【推荐】
如同开发一个api接口一样。对于任何后端开发都能快速找到位置,并进行拓展。只需要关注业务即可。并且需要的资源类,直接IOC注入即可使用。扩展起来比较方便。
支持JWT认证时,需要创建定义JwtAuthenticationFilter
,JwtAuthenticationToken
,JwtAuthenticationProvider
类,完成jwt认证流程类的实现。包括Jwt生成工具和解析工具。
JwtAuthenticationFilter
jwt认证准入规则校验,jwt认证流程的实现。
OncePerRequestFilter
的子类
JwtAuthenticationToken
jwt认证的token类。
AbstractAuthenticationToken
的子类。Jwt Provider认证的支持类
JwtAuthenticationProvider
AuthenticationProvider
的子类, 主要提供对JwtAuthenticationToken
的认证逻辑的具体实现类
implementation "org.springframework.boot:spring-boot-starter-security"
@EnableWebSecurity
public class Application
认证流程需要的实例
自定义认证涉及类 | 作用 | 描述 |
---|---|---|
默认用户名密码认证 | 禁用默认 | |
PasswordEncoder | 密码加密器 | |
DaoAuthenticationProvider | 数据库认证供应商 | 默认 |
AuthenticationManager | 认证管理者 | new ProviderManager(authenticationProviders); |
JwtAuthenticationFilter | jwt认证过滤器 | 自定义:主要jwt准入条件和封装认证token |
JwtAuthenticationProvider | jwt认证供应商 | 自定义:主要对认证token进行验证 |
SecurityFilterChain | spring security核心类 | HttpSecurity配置build |
CorsConfigurationSource | cors配置类 | 自定义配置 |
AccessDeniedHandler | 权限校验失败 | 自定义子类实现【ExceptionTranslationFilter使用】 |
AuthenticationEntryPoint | 认证失败处理 | 自定义子类实现【ExceptionTranslationFilter使用】 |
JwtAuthenticationToken | jwt token 认证凭证类 | AbstractAuthenticationToken子类 |
IdentificationService | 认证接口服务 | 替代 |
AuthenticationFailureHandler和AuthenticationSuccessHandler未使用。因为UsernamePasswordAuthenticationFilter禁用了。所以该两个就无效使用。
代码 - spring3.0版本-企业web后端 - kongxiang (gitee.com)