本文暂未完善
SpringSecurity的逻辑架构主要分为两部分:认证架构和授权架构
Servlet 认证架构
总体架构:
关键组件:
AuthenticationFilter
:用于获取请求中的信息,并创建 Authentication
对象
AuthenticationProvider
:用于验证登录逻辑,对Authentication
进行进一步的身份认证
用户携带认证token进行请求,请求中的用户身份信息会被AuthenTicationFilter提取出来并交给AuthenticationManager
,AuthenticationManager
负责对用户的身份信息进行认证
逻辑关系
ProviderManager
ProviderManager中包含了一系列的Provider,这些Provider负责执行实际的身份验证。例如,DaoAuthenticationProvider
支持基于用户名/密码的身份验证,同时JwtAuthenticationProvider
支持对 JWT 令牌进行身份验证。每个AuthenticationProvider
执行特定类型的身份验证。
DaoAuthenticationProvider
输入Username和Password,返回UserDetails和Authorities
作用:是一个AuthenticationProvider
,用于校验账号密码
SecurityContextHolder
Spring Security 身份验证模型的核心是SecurityContextHolder
,它存在于TreadLocal中
设置SecurityContextHolder
不能直接通过SecurityContextHolder.getContext().setAuthentication(authentication)
来设置Holder中的context,否则多线程情况下会出现问题。应该为每个线程创建单独的实例:
1 | SecurityContext context = SecurityContextHolder.createEmptyContext(); |
访问当前经过身份验证的用户
1 | SecurityContext context = SecurityContextHolder.getContext(); |
- 默认情况下,SecurityContextHolder使用
ThreadLocal
来存储这些详细信息。 - ThreadLocal如果在处理当前主体的请求后注意清除线程,Spring Security 的
FilterChainProxy
确保SecurityContext始终清除。 - 三者包含关系:SecurityContextHolder→ SecurityContext → Authentication
Authentication
中包含:
principal
:标识用户。当使用用户名/密码进行身份验证时,这通常是UserDetails.credentials
: 通常是密码。很多情况下,这个是在用户通过认证后清除的,以保证不被泄露。Collection<? extends GrantedAuthority>
:GrantedAuthority实例是授予用户的高级权限。
UserDetails
、UserDetailsService
关系:UserDetails由UserDetailsService返回。
DaoAuthenticationProvider
验证UserDetails,然后返回一个Authentication,该Authentication的主体是配置的UserDetailsService返回的UserDetails。