Spring-Security 认证流程分析及多方式登录认证实践
程序员的成长之路
共 6415字,需浏览 13分钟
·
2024-08-18 07:34
阅读本文大概需要 4 分钟。
来自:juejin.cn/post/7329144188926967860
1 前言
spring-security
,在本文中将介绍 spring-security
的工作流程和实践应用,并基于此总结其使用心得和项目配置关键。
2 spring security 认证和权限流程
DefaultSecurityFilterChain
,绿色的部分负责用户认证,蓝色的部分处理认证异常的情况,橙色的部分负责用户的授权,最终请求到控制器的方法。在认证完成之后,会将用户认证的结果 Authentication
放进 SecurityContextHolder
中,从中可以获取到用户信息。
-
SecurityContextHolder: 存放身份信息的容器 -
Authentication: 用户信息的抽象即 security 的认证主体 -
AbstractAuthenticationToken: authentication
即认证主体的抽象类, -
AuthenticationManager: 身份认证器接口,具体实现类为 ProviderManager
-
AuthenticationProvider: 用来处理 authentication
的认证信息 -
AuthenticationSuccessHandler 认证成功处理器 -
AuthenticationFailureHandler 认证失败处理器
authentication
封装其认证方法,通过 AuthenticationProvider
来进行处理认证。获取身份信息会按照其配置provider的顺序来处理。
Authentication
下的实现类UsernamePasswordAuthenticationToken
, 通常是用户密码的登录方式。
AuthenticationManager
身份管理器,通过其配置的provider 验证这个UsernamePasswordAuthenticationToken
的信息。
AuthenticationManager.authentication
身份管理器返回一个Authentication
实例(上下文中包含权限信息,身份信息,细节信息,但是密码会被移除)。
SecurityContextHolder
上下文容器会填充UsernamePasswordAuthenticationToken
信息,通过 SecurityContextHolder.getContext().setAuthentication()
方法可以查看其上下文用户信息。
3 spring security 登录配置
-
登录请求不拦截 permitAll
-
资源需要某些角色 hasRole
-
资源访问需要某些权限 hasAuthority
-
其它的资源需要经过认证,在资源权限上的配置也可以通过注解的方式在控制器中设置
successForwardUrl
是请求转发的方式,defaultSuccessUrl
是重定向的方式。
session
和 authentication
的处理。
session
的管理,通常情况下在前后端不分离的情况下,需要用 session 进行管理,在前后端分离的情况下,一般通过 token 的方式来存储用户信息。maximumSessions
表示最大的用户登录数量。
accessDeniedHandler
即权限异常处理器
token
的配置信息,以及记住我的参数信息。
csrf/cors/frameoptions/cache
的配置方式。
addFilterAt/addFilterAfter/addFilterBefore
的方式来处理自定义的过滤器。
spring-security
的其它配置如下所示,可以配置信息提示的国际化,身份认证的方式,自定义 AuthenticationManager
,以及配置token 的持久化方式,这里包括内存方式和数据库方式。
KaptchaFilter
是用来配置验证码的处理,通常情况下登录需要需要 post 的方式,对于验证码的处理方式,需要先生成验证码存储到内存中,然后登录时需要携带验证码参数来进行校验而后进行下一个过滤器处理。
http method
保持一致。
4 spring security 表单认证流程
SecurityContextPersistenceFilter
拦截所有的请求,共享会话将 session 中的 SecurityContext
信息放进线程上下文中。
AbstractAuthenticationProcessingFilter
判断是否需要认证,需要认证就获取认证 Authentication
,然后放进 session 中。
UsernamePasswordAuthenticationFilter
创建 UsernamePasswordAuthenticationToken
进行认证,委托 ProviderManager
(即 AuthenticationManager
) 发起认证,由多个 AuthenticationProvider
接口列表组成进行循环处理。
DaoAuthenticationProvider
调用 UserDetailsService
方法进行用户查询,最终返回 AuthenticationToken
即 UsernamePasswordAuthenticationToken
ExceptionTranslationFilter
进行处理
FilterSecurityInterceptor
中体现,判断用户是否有权限访问资源。
5 手机号和邮箱验证码登录
spring security
认证相关的内容,通常情况下,系统的登录不仅有账号密码登录,还有手机号验证码、第三方授权等登录多种方式,在接下来将要介绍的就是手机号验证码登录和邮箱登录的方式。
-
继承 AbstractAuthenticationProcessingFilter
,重写attemptAuthentication
用于获取登录提交参数,并校验验证码是否正确 -
继承 AuthenticationProvider
,重写authenticate
方法,从数据库查询用户信息,并完成AuthenticationToken
对象封装。 -
继承 AbstractAuthenticationToken
, 重写构造方法,完成对象封装以及授权。
-
调用发送验证码接口,发送验证码,本例是在控制台打印验证码。 -
通过表单或者json格式都可以提交信息完成认证。 -
用户认证成功或者失败时,通过认证成功或者失败处理器进行处理,返回 json 数据格式或者是页面。
spring security
相关的认证流程和认证成功的处理方式,此外,还可以通过如下方式,通过注入 AuthenticationManager
调用认证方式来处理用户认证信息。
6 总结
spring security
登录相关的核心配置,以及验证码方式登录的实践, spring security
作为系统开发中常用的权限认证框架,在此基础上拓展了项目的多种登录方式,即手机验证码和邮箱验证码的方式,同时也介绍了前后端分离与不分离情况下的差异。
spring security
常用的使用方式,可以很好的为后续开发提供借鉴。所涉及的代码已经上传至 gitee:https://gitee.com/xieyue86/springsecurity-learn
推荐阅读:
几行代码,搞定 SpringBoot 接口恶意刷新和暴力请求!
程序员在线工具站:cxytools.com 推荐一个自己写的工具站:http://cxytools.com,专为程序员设计,包括时间日期、JSON处理、SQL格式化、随机字符串生成、UUID生成、文本Hash...等功能,提升开发效率。
⬇戳阅读原文直达! 朕已阅
评论