`
kong0itey
  • 浏览: 304868 次
社区版块
存档分类
最新评论

《Spring Security3》第六章第六部分翻译(Spring Security基于bean的高级配置)

阅读更多

Spring Security 基于bean 的高级配置

 

正如我们在前面几页中看到的那样,基于 bean Spring Security 配置尽管比较复杂,但是提供了一定层次的灵活性,如果复杂应用需要超过 security XML 命名空间风格配置所允许的功能时会用到。

         我们将利用这个章节来阐明可用的一些配置选项以及怎么使用。尽管我们不能提供每个可能属性的细节,但是我们鼓励基于在本章和以前章节学到的内容你开始探索并查询 Javadoc Spring Security 的源码。你仅仅会受限于对这个框架是如何组织起来的知识和你的想象力。

Session 生命周期的调整元素

         Spring Security 有很多地方影响用户的 HttpSession 的生命周期。有很多功能只有将相关类配置成 Spring bean 时才可用。以下的表格列出了能够影响 session 创建和销毁的 bean 属性:

Class (类)

属性

默认值

描述

AbstractAuthentication ProcessingFilter 

UsernamePasswordAuthenticationFilter 的父类)  

allowSessionCreation

true

如果为 true ,当认证失败时创建一个新的 session (存储异常)

UsernamePasswordAuthenticationFilter

allowSessionCreation

true

如果为 true 的话,这个特殊的过滤器将会创建一个 session 存储最后尝试的用户名。

SecurityContextLogoutHandler

invalidateHttpSession

true

如果为 true HttpSession 将会失效(参考 Servlet 规范了解 session 失效的细节)

SecurityContextPersistenceFilter

forceEagerSessionCreation

false

如果为 true ,该过滤器将会在执行链中其它过滤器之前创建一个 session

HttpSessionSecurityContextRepository

allowSessionCreation

true

如果为 true ,如果在请求结束时 session 中还没有 SecurityContext 的话, SecurityContext 将存储到 session 中。

 

         取决于你应用的需要,需要审慎分析用户 session ——包括认证的和非认证的——并调整相应的 session 生命周期。

手动配置其它通用的服务

         还有一些其它的服务,我们已经在 security 命名空间自动配置中使用了。让我们将其添加上,这样就会有一个完整的基本配置实现。

声明缺失的过滤器

         我们将要增强手动配置的过滤器链,添加三个我们还没有配置的服务。包含处理退出、 remember me 以及异常转换。一旦我们完成这些过滤器,我们将会有完整的功能并可以在它启动时深入了解一些有趣的配置选项。

         以下缺失的过滤器将会添加到我们的过滤器链中:

 

Xml代码  收藏代码
  1. < bean   id = "springSecurityFilterChain"    
  2.   class = "org.springframework.security.web.FilterChainProxy" >   
  3.   < security:filter-chain-map   path-type = "ant" >   
  4.     < security:filter-chain   pattern = "/**"   filters ="  
  5.       securityContextPersistenceFilter,  
  6.       logoutFilter,  
  7.       usernamePasswordAuthenticationFilter,  
  8.       rememberMeAuthenticationFilter,  
  9.       anonymousAuthenticationFilter,  
  10.       exceptionTranslationFilter,  
  11.       filterSecurityInterceptor" />   
  12.   </ security:filter-chain-map >   
  13. </ bean >   

 正如在前面做的那样,现在我们需要声明这些 Spring bean 并配置他们以及所有依赖的服务 bean

 

LogoutFilter

         LogoutFilter 的基本配置(它默认用来响应虚拟 URL  /j_spring_security_logout )如下:

 

Xml代码  收藏代码
  1. < bean   id = "logoutFilter"   class ="org.springframework.security   
  2.   .web.authentication.logout.LogoutFilter">   
  3.   <!-- the post-logout destination -->   
  4.   < constructor-arg   value = "/" />   
  5.     < constructor-arg >   
  6.       < array >   
  7.         < ref   local = "logoutHandler" />   
  8.       </ array >   
  9.     </ constructor-arg >   
  10.   < property   name = "filterProcessesUrl"   value = "/logout" />   
  11. </ bean >   

 你会发现构造 LogoutFilter 的方法与其它的认证过滤器都不一样,使用了构造方法而不是 bean 属性。第一个构造参数是用户退出后要转向的 URL ,第二个参数是对 LogoutHandler 实例的引用。

【依赖注入中的构造器哲学。如果你使用 Spring 有一段时间了,可能已经讨论过以适当的面向对象方式管理需要的依赖。尽管 setter 方式对 Spring 的用户来说很便利,但是追求纯正面向对象的人经常会认为如果一个依赖影响到类的功能,那它应该是构造方法签名的一部分(思考一下在 Spring 以前你是怎样写类的)。鉴于 Spring Security 已经发展了有些年头,不同的作者对此有不同的观点,而我们碰巧正好遇到一个或两个这方面的不一致。两种风格的依赖模型都可以——到底使用哪种风格其实取决于你喜欢哪种类型的需求依赖模型。】

         我们还要声明一个简单的 LogoutHandler 的如下:

 

Xml代码  收藏代码
  1. < bean   id = "logoutHandler"   class ="org.springframework.security   
  2.   .web.authentication.logout.SecurityContextLogoutHandler"/>   

 你可能认出这个 LogoutHandler 在我们前几页关于 session 处理的表格中出现过。一个明确配置 logout 处理器的好处就是你能修改用户退出时默认的 session 处理行为。一旦我们完成这两点的配置, Log Out 链接就能够再次开始工作了。

         请记住在第三章 security 命名空间配置中,我们曾经修改应用使用一个不那么明显绑定 Spring Security 的退出 URL 。当我们从 security 命名空间配置方式修改为明确 bean 定义时,这是我们在这个 bean 定义时重写 filterProcessesUrl 属性的原因,以保持应用的配置保持持续性。

RememberMeAuthenticationFilter

         你可能也会回忆起在第三章中使用的 remember me 功能。即使在基于 bean 的配置中,我们也要保持这个有用的 remember me 功能。这关系到一个新的过滤器、新的支持 bean 以及修改一些其它的 bean 。首先让我们看一下这个过滤器:

 

Xml代码  收藏代码
  1. < bean   id = "rememberMeAuthenticationFilter"    
  2.   class ="org.springframework.security.web   
  3.   .authentication.rememberme.RememberMeAuthenticationFilter">   
  4.   < property   name = "rememberMeServices"   ref = "rememberMeServices" />   
  5.   < property   name = "authenticationManager"    ref = "customAuthenticationManager"   />   
  6. </ bean >   

 你会发现对 rememberMeServices 的引用,而它还没有定义。现在让我们定义这个 bean

 

Xml代码  收藏代码
  1. < bean   id = "rememberMeServices"    
  2.   class ="org.springframework.security.web.authentication   
  3.   .rememberme.PersistentTokenBasedRememberMeServices">   
  4.   < property   name = "key"   value = "jbcpPetStore" />   
  5.   < property   name = "tokenValiditySeconds"   value = "3600" />   
  6.   < property   name = "tokenRepository"   ref = "jdbcRememberMeTokenRepository" />   
  7.   < property   name = "userDetailsService"   ref = "jdbcUserService" />   
  8. </ bean >   

 RememberMeServices 实现的很多配置属性与 security 命名空间风格的配置很相似。这两种方法的最大不同是 RememberMeServices 从应用配置的细节中抽象出来了(译者注:即在 security 方式的配置中,已经进行了一些抽象),但是在基于 bean 的配置中, bean 声明必须非常了解在 remember me 功能中所关联的所有 bean 。如果你感到迷惑,请回顾第三章到第四章以了解 remember me 功能所关联的类和流程的细节。

         我们有另一个 bean 应用来织入 remember me token 存储。这个 bean 定义很简单,如下:

 

Xml代码  收藏代码
  1. < bean   id = "jdbcRememberMeTokenRepository"    
  2.   class ="org.springframework.security.web   
  3.   .authentication.rememberme.JdbcTokenRepositoryImpl">   
  4.   < property   name = "dataSource"   ref = "dataSource" />   
  5. </ bean >   

 最后我们需要声明 AuthenticationProvider ,它负责处理 remember me 认证请求。它的声明如下:

 

Xml代码  收藏代码
  1. < bean   id = "rememberMeAuthenticationProvider"    
  2.   class = "org.springframework.security .authentication.RememberMeAuthenticationProvider" >   
  3.   < property   name = "key"   value = "jbcpPetStore" />   
  4. </ bean >   

 你可能会记得这个 key 属性在 AuthenticationProvider (用来进行 token 校验)和 RememberMeServices (用来进行 token 生成)之间共享。要保证它们被设置成相同的。你可能想通过一个 properties 文件来设置这个属性值,那是要 PropertyPlaceholderConfigurer 工具类(或其它类似的)。

         现在我们需要将这个 AuthenticationProvider 织入到 AuthenticationManager 的列表中。

 

Xml代码  收藏代码
  1. < bean   id = "customAuthenticationManager"    
  2.   class = "org.springframework.security .authentication.ProviderManager" >   
  3.   < property   name = "providers" >   
  4.     < list >   
  5.       < ref   local = "daoAuthenticationProvider" />   
  6.       < ref   local =”anonymousAuthenticationProvider” />   
  7.       < ref   local = "rememberMeAuthenticationProvider" />   
  8.     </ list >   
  9.   </ property >   
  10. </ bean >   

 RememberMeServices 必须织入到 UsernamePasswordAuthenticationFilter ,这样 RememberMeServices 就能处理明确的登录成功( remember me cookie 被更新)和失败( remember me 被移除)。(译者注:其实查看源码在登录失败时,没有移除 cookie 的操作)

 

Xml代码  收藏代码
  1. < bean   id = "usernamePasswordAuthenticationFilter"    
  2.   class ="org.springframework.security.web   
  3.   .authentication.UsernamePasswordAuthenticationFilter">   
  4.   < property   name = "authenticationManager"    
  5.   ref = "customAuthenticationManager" />   
  6.   < property   name = "rememberMeServices"   ref = "rememberMeServices" />   
  7. </ bean >   

 最后要记住的一件事(在配置 Spring Security bean 声明时,用户经常遗忘) RememberMeServices 也是 LogoutHandler 功能的一部分,它在用户退出时清理用户的 cookie

 

Xml代码  收藏代码
  1. < bean   id = "logoutFilter"    
  2.   class = "org.springframework.security.web .authentication.logout.LogoutFilter" >   
  3.   < constructor-arg   value = "/" />   
  4.   < constructor-arg >   
  5.     < array >   
  6.       < ref   local = "logoutHandler" />   
  7.       < ref   local = "rememberMeServices" />   
  8.     </ array >   
  9.   </ constructor-arg >   
  10.   < property   name = "filterProcessesUrl"   value = "/logout" />   
  11. </ bean >   

 当这些配置到位,我们就完成了明确织入 remember me 功能。你可能没有想到过 <remember-me> 声明在幕后做了多少的工作。

ExceptionTranslationFilter

         Spring Security 标准的过滤器链中最后一个 servlet 过滤器是 ExceptionTranslationFilter 。从本章我们前面的讨论,回忆一下这个过滤器在认证和授权整个流程中的重要性。最后的这个过滤器需要一个过滤器定义和两个支持 bean

 

Xml代码  收藏代码
  1. < bean   id = "exceptionTranslationFilter"    
  2.   class = "org.springframework.security.web .access.ExceptionTranslationFilter" >   
  3.   < property   name = "authenticationEntryPoint"   ref = "authenticationEntryPoint" />   
  4.   < property   name = "accessDeniedHandler"   ref = "accessDeniedHandler" />   
  5. </ bean >   

 支持 bean 的声明如下:

 

Xml代码  收藏代码
  1. < bean   id = "authenticationEntryPoint"    
  2.   class ="org.springframework.security.web   
  3.   .authentication.LoginUrlAuthenticationEntryPoint">   
  4.   < property   name = "loginFormUrl"   value = "/login.do" />   
  5. </ bean >   
  6. < bean   id = "accessDeniedHandler"    
  7.   class = "org.springframework.security.web .access.AccessDeniedHandlerImpl" >   
  8.   < property   name = "errorPage"   value = "/accessDenied.do" />   
  9. </ bean >   

 你可能会认出 errorPage 指令定义的 Access Denied 页面就是本章前面访问拒绝配置练习中的那个地址。类似的, loginFormUrl 对应于我们在前面看到的 security 命名空间中的 login-page 属性。

明确配置SpEL 表达式和投票器

         让我们看一下与 security 命名空间中 use-expressions="true" 属性等同的 Spring bean 配置:

 

Xml代码  收藏代码
  1. < bean   class ="org.springframework.security   
  2.   .web.access.expression.DefaultWebSecurityExpressionHandler"   
  3.   id = "expressionHandler" />   

 接下来,我们需要建立投票器( Voter )指向表达式处理器,如下:

 

Xml代码  收藏代码
  1. < bean   class ="org.springframework.security.web.access   
  2.   .expression.WebExpressionVoter" id = "expressionVoter" >   
  3.   < property   name = "expressionHandler"   ref = "expressionHandler" />   
  4. </ bean >   

 最后,我们需要使 AccessDecisionManager bean 使用这个投票器。

 

Xml代码  收藏代码
  1. < bean    class = "org.springframework.security.access.vote.AffirmativeBased"    
  2. id = "affirmativeBased" >   
  3.   < property   name = "decisionVoters" >   
  4.     < list >   
  5.       < ref   bean = "expressionVoter" />   
  6.     </ list >   
  7.   </ property >   
  8. </ bean >   

 在完成这些配置以后,我们回到了使用 use-expressions="true" 默认设置的那个点上(译者注:即与使用命名空间配置 use-expressions="true" 一样的效果)。但是,既然我们使用了明确配置方式,那么可以使用自定义的类替换默认的某个或全部类。我们将会本章后面的部分看一个这样的例子。

基于 bean 配置方法安全

         在第五章中,我们使用 security 命名空间 <global-method-security> 声明的方式配置过方法安全。迁移到明确的、基于 bean 的配置时,我们必须配置需要的主要类和支持类以重写 <global-method-security> 声明的功能。

         我们在第五章中,已经开发出完整的以 bean 配置的方法安全,支持各种类型的注解。鉴于这个配置很简单直接,基本上没有什么有意思的属性,所以我们将完整的配置放在附录:参考资料 中以及本章的 dogstore-explicit-base.xml 配置文件里面。

包装明确的配置

         到此时,我们已经完成了配置基于 bean Spring security ,应用也是功能完整的了。如果你想体验 security 命名空间风格的配置与 bean 声明的配置,很容易修改 web.xml 中对 Spring 配置文件的引用从而把一系列配置文件的集合切换到另一个。

l  security 命名空间的配置文件为 web.xml 引用的 dogstore-base.xml dogstore-security.xml

l  基于 bean 的配置文件为 web.xml 引用的 dogstore-explicit-base.xml

从此往后,本书的练习中将会假设你使用的是 security 命名空间配置。如果特定的功能只能使用基于 bean 的配置,我们将会明确说明。我们也会包含一些基于 bean 配置的细节,因为我们知道一些开发人员更愿意拥有这个级别上对安全框架的控制。

我们应该选择什么类型的配置呢?

         希望你的大脑没有从我们刚才的所有配置中变迷糊。你可能会想知道,对于一个典型的工程,应该选择什么类型的配置呢。正如你可能预料的那样,答案是取决于你项目的复杂性以及你重写或自定义 Spring Security 元素的程度。

配置类型

好处

security 命名空间

l  强大、简洁语法,适用于通常的 web 和方法安全配置;

l  用户配置复杂功能时,并不需要知道组件在幕后是如何交互的;

l  security 命名空间进行代码检查和并警告多种潜在的配置缺陷;

l  明显减少缺失配置步骤的可能性。

明确的 bean 定义

l  允许最大灵活性以扩展、重写以及删节标准的 Spring Security 功能;

l  允许自定义过滤器链及根据 URL 模式(使用 <filter-chain> 元素的 pattern 属性)的认证方法。这可能在混合 web service REST 认证以及用户认证时用到;

l  不用直接将配置文件绑定到 Spring Security 命名空间处理上;

l  认证管理器可以明确配置或重写;

l  与更简单的 security 命名空间相比,暴露了有更多的配置选项。

 

         对于大多数项目,比较明智的是以 security 命名空间开始,并在可能的情况下继续使用直到你的应用需要它不满足的功能。要记住的是,自己配置所有需要的 bean bean 间的依赖关系将会明显增加复杂度,在开始之前,你应该对 Spring Security 的结构(可能还包括底层代码)有清晰的理解。

分享到:
评论

相关推荐

    Spring Security3中文文档

    此外,还涉及了如何手动配置Spring Security的bean以及基于bean的高级配置。 ### 第七章:访问控制列表(Access Control List, ACL) 这一章节介绍了ACL的概念和用法,包括如何创建高级ACL以及使用ACL时需要注意的...

    SpringSecurity 3配置文件

    在本文中,我们将深入探讨Spring Security 3的配置文件,以及如何理解和使用这些配置来增强应用的安全性。 首先,Spring Security的配置通常位于一个或多个XML文件中,这些文件通过`&lt;beans&gt;`标签定义了安全相关的...

    bean配置跑spring security(mysql数据库)_spring security例子

    通过以上步骤,我们可以成功地将Spring Security与MySQL数据库集成,实现基于bean配置的用户认证和授权。博客作者`dsundsun`可能在CSDN上提供了更详细的过程和代码示例,帮助读者深入了解这一主题。在实践中,理解...

    spring security3 开发手册

    Spring Security是一个功能强大且可高度定制的身份验证和访问控制框架,它是保护基于Spring的应用程序的事实标准。Spring Security 3作为该框架的一个版本,提供了丰富的安全性配置选项,涵盖了从基础的认证和授权到...

    spring security 使用及配置

    Spring Security 使用及配置 Spring Security 是一个基于 Java 的安全框架,提供了丰富的安全功能,包括身份验证、授权、加密、会话管理等。下面将对 Spring Security 的使用及配置进行详细介绍。 身份验证 身份...

    Spring Security 3 与 CAS单点登录配置.doc

    Spring Security 3 与 CAS 单点登录配置 Spring Security 3 是一个基于 Java 的安全框架,提供了灵活的身份验证、授权和访问控制功能。CAS(Central Authentication Service)是一种流行的单点登录协议,允许用户...

    spring cloud2.0 eureka server spring security配置

    在Spring Cloud 2.0版本中,Eureka Server的配置相比1.x版本确实有了一些显著的变化,尤其是在结合Spring Security进行安全设置时。Spring Cloud Eureka是Netflix Eureka的Spring Boot实现,它为微服务架构提供了...

    spring-security多个登录页面配置

    在Spring Security框架中实现多个登录页面的配置是一项高级特性,主要应用于区分前端用户与后端管理员的不同登录需求。本文将详细介绍如何通过Spring Security配置多个登录页面,并为不同类型的用户设置不同的登录...

    SpringSecurity.zip

    它提供了一组可以在Spring应用上下文中配置的Bean,充分利用了Spring IoC,DI(控制反转Inversion of Control ,DI:Dependency Injection 依赖注入)和AOP(面向切面编程)功能,为应用系统提供声明式的安全访问控制...

    Spring Security 3 与 CAS单点登录配置-Server

    标题 "Spring Security 3 与 CAS 单点登录配置 - Server" 涉及到的是在企业级应用中实现安全访问控制的重要技术。Spring Security 是一个强大的和高度可定制的安全框架,用于保护基于 Java 的 Web 应用程序。而 CAS...

    Spring Security3

    ### Spring Security 3 权限管理关键知识点解析 #### 一、Spring Security 3 概述 Spring Security 是一个强大的且高度可定制的身份验证和访问控制框架,它为基于 Java 的应用程序提供了广泛的保护机制。Spring ...

    spring security3配置和使用

    ### Spring Security3 配置与使用详解 #### 一、Spring Security3 概览 Spring Security 是一个功能强大且高度可定制的身份验证和访问控制框架。最初由 Ben Alex 在 2003 年创建,名为 "The Acegi Security System...

    Restful风格服务端应用的Spring Boot + Spring Security配置

    配置Spring Security的第一步是添加相关依赖。在`pom.xml`文件中,我们需要引入`spring-boot-starter-security`和`spring-boot-starter-web`,这将为我们提供安全服务和Web支持。 ```xml &lt;groupId&gt;org.spring...

    spring security3配置

    &lt;beans:bean id="myAccessDecisionManagerBean" class="springSecurity.MyAccessDecisionManager"&gt; &lt;!-- 配置项 --&gt; &lt;/beans:bean&gt; &lt;!-- 安全元数据源 --&gt; &lt;beans:bean id="securityMetadataSource" class=...

    初识 Spring Security - v1.1.pdf

    通过以上详细解析,可以看出Spring Security是一个非常强大且灵活的安全框架,它不仅能够满足基本的认证需求,还提供了丰富的高级特性,如权限管理、Remember-Me功能、session管理等。这对于构建安全可靠的企业级...

    Spring_Security_多页面登录配置教程

    ### Spring Security 多页面登录配置教程 #### 一、引言 在开发Web应用程序时,安全性和用户体验同样重要。Spring Security作为一个强大的框架,为开发者提供了丰富的功能来保护Web应用的安全。其中,支持多页面...

    Spring Security、Spring Social 、Spring Security OAuth

    它提供了一组可以在Spring应用上下文中配置的Bean,充分利用了Spring IoC,DI(控制反转Inversion of Control ,DI:Dependency Injection 依赖注入)和AOP(面向切面编程)功能,为应用系统提供声明式的安全访问控制...

    Spring Security3 中文版 张卫滨 推荐

    ### 第六章:高级配置和扩展 最后这一章介绍了如何通过扩展Spring Security的功能来满足更加复杂的需求。 - **实现一个自定义的安全过滤器**: - **在servlet过滤器级别实现IP过滤**:提供了如何根据IP地址来限制...

    SPRING SECURITY配置

    **Spring Security配置详解** Spring Security是一款强大的安全框架,它为Java应用提供了全面的安全服务,包括认证、授权和访问控制。本文将深入探讨Spring Security的核心概念、配置方式以及常见应用场景。 ### 1...

    springSecurity.zip

    Spring Security 是一个强大的和高度可定制的身份验证和访问控制框架,用于保护基于Java的Web应用程序。它是Spring生态系统的一部分,提供了一套完整的安全解决方案,包括登录、授权、会话管理、CSRF防护等功能。本...

Global site tag (gtag.js) - Google Analytics