文章目录
- 架构主要组件
- SecurityContextHolder
- Authentication
- AuthenticationManager
- ProviderManager
- AuthenticationProvider
- AuthenticationEntryPoint
- AbstractAuthenticationProcessingFilter
架构主要组件
- SecurityContextHolder - SecurityContextHolder 是 Spring Security 存储 认证 用户细节的地方。
- SecurityContext - 是从 SecurityContextHolder 获得的,包含了当前认证用户的 Authentication (认证)。
- Authentication - 可以是 AuthenticationManager 的输入,以提供用户提供的认证凭证或来自 SecurityContext 的当前用户。
- GrantedAuthority - 在 Authentication (认证)中授予委托人的一种权限(即role、scope等)。
- AuthenticationManager - 定义 Spring Security 的 Filter 如何执行 认证 的API。
- ProviderManager - 最常见的 AuthenticationManager 的实现。
- AuthenticationProvider - 由 ProviderManager 用于执行特定类型的认证。
- AuthenticationEntryPoint - 请求凭证,用于从客户端请求凭证(即重定向到登录页面,发送 WWW-Authenticate 响应,等等)。
- AbstractAuthenticationProcessingFilter - 一个用于认证的基本 Filter。这也让我们很好地了解了认证的高层流程以及各部分是如何协作的。
SecurityContextHolder
Spring Security 的认证模型的核心是 SecurityContextHolder。它包含了SecurityContext。
- SecurityContextHolder 是 Spring Security 存储用户 验证 细节的地方。Spring Security 并不关心 SecurityContextHolder 是如何被填充的。如果它包含一个值,它就被用作当前认证的用户。
Authentication
-
Authentication 接口在Spring Security中主要有两个作用。
- 对 AuthenticationManager 的一个输入,用于提供用户为验证而提供的凭证。当在这种情况下使用时,isAuthenticated() 返回 false。
- 代表当前认证的用户。你可以从 SecurityContext 中获得当前的 Authentication。
-
认证(Authentication)包含了:
- principal: 识别用户。当用用户名/密码进行认证时,这通常是 UserDetails 的一个实例。
- credentials: 通常是一个密码。在许多情况下,这在用户被认证后被清除,以确保它不会被泄露。
- authorities: GrantedAuthority 实例是用户被授予的高级权限。两个例子是角色(role)和作用域(scope)。
AuthenticationManager
- AuthenticationManager 是定义 Spring Security 的 Filter 如何执行 认证 的API。返回的 认证是由调用 AuthenticationManager 的控制器(即 Spring Security的 Filter 实例)在 SecurityContextHolder 上设置的。如果你不与 Spring Security 的 Filter 实例集成,你可以直接设置 SecurityContextHolder,不需要使用 AuthenticationManager。
- 虽然 AuthenticationManager 的实现可以是任何东西,但最常见的实现是ProviderManager。
ProviderManager
- ProviderManager是最常用的AuthenticationManager的实现。ProviderManager 委托给一个 ListAuthenticationProvider实例。每个 AuthenticationProvider 都有机会表明认证应该是成功的、失败的,或者表明它不能做出决定并允许下游的 AuthenticationProvider 来决定。如果配置的 AuthenticationProvider 实例中没有一个能进行认证,那么认证就会以 ProviderNotFoundException 而失败,这是一个特殊的 AuthenticationException,表明 ProviderManager 没有被配置为支持被传入它的 Authentication 类型。
AuthenticationProvider
- 可以在 ProviderManager 中注入多个 AuthenticationProvider 实例。每个 AuthenticationProvider 都执行一种特定类型的认证。例如, DaoAuthenticationProvider 支持基于用户名/密码的认证,而 JwtAuthenticationProvider 支持认证JWT令牌。
AuthenticationEntryPoint
- AuthenticationEntryPoint 用于发送一个要求客户端提供凭证的HTTP响应。
- 有时,客户端会主动包含凭证(如用户名和密码)来请求资源。在这些情况下,Spring Security 不需要提供要求客户端提供凭证的HTTP响应,因为这些凭证已经被包括在内。
- 在其他情况下,客户端向他们未被授权访问的资源发出未经认证的请求。在这种情况下, AuthenticationEntryPoint 的实现被用来请求客户端的凭证。 AuthenticationEntryPoint 的实现可能会执行 重定向到一个登录页面,用 WWW-Authenticate 头来响应,或采取其他行动。
AbstractAuthenticationProcessingFilter
- AbstractAuthenticationProcessingFilter 被用作验证用户凭证的基础 Filter。在认证凭证之前,Spring Security 通常通过使用AuthenticationEntryPoint 来请求凭证。
- 接下来,AbstractAuthenticationProcessingFilter 可以对提交给它的任何认证请求进行认证。
- 当用户提交他们的凭证时,AbstractAuthenticationProcessingFilter 会从 HttpServletRequest 中创建一个要认证的Authentication。创建的认证的类型取决于 AbstractAuthenticationProcessingFilter 的子类。例如,UsernamePasswordAuthenticationFilter从 HttpServletRequest 中提交的 username 和 password 创建一个 UsernamePasswordAuthenticationToken。
- 接下来,Authentication 被传入 AuthenticationManager,以进行认证。
- 如果认证失败,则为 Failure。
- SecurityContextHolder 被清空。
- RememberMeServices.loginFail 被调用。如果没有配置记住我(remember me),这就是一个无用功。
- AuthenticationFailureHandler 被调用。
- 如果认证成功,则为 Success。
- SessionAuthenticationStrategy 被通知有新的登录。
- Authentication 被设置在 SecurityContextHolder 上。之后, SecurityContextPersistenceFilter 会将 SecurityContext 保存到 HttpSession 中。
- RememberMeServices.loginSuccess 被调用。如果没有配置 remember me,这就是一个无用功。
- ApplicationEventPublisher 发布一个 InteractiveAuthenticationSuccessEvent 事件。
- AuthenticationSuccessHandler 被调用。
你知道的越多,你不知道的越多。