`
lengyun3566
  • 浏览: 446635 次
  • 性别: Icon_minigender_1
  • 来自: 大连
博客专栏
D59180b9-02f1-3380-840c-ea34da46143c
《Spring Secur...
浏览量:379200
社区版块
存档分类
最新评论

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

阅读更多


Spring Security
基于bean的高级配置

 

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

         我们将利用这个章节来阐明可用的一些配置选项以及怎么使用。尽管我们不能提供每个可能属性的细节,但是我们鼓励基于在本章和以前章节学到的内容你开始探索并查询JavadocSpring 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

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

SecurityContextPersistenceFilter

forceEagerSessionCreation

false

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

HttpSessionSecurityContextRepository

allowSessionCreation

true

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

 

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

手动配置其它通用的服务

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

声明缺失的过滤器

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

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

 

<bean id="springSecurityFilterChain" 
  class="org.springframework.security.web.FilterChainProxy">
  <security:filter-chain-map path-type="ant">
    <security:filter-chain pattern="/**" filters="
      securityContextPersistenceFilter,
      logoutFilter,
      usernamePasswordAuthenticationFilter,
      rememberMeAuthenticationFilter,
      anonymousAuthenticationFilter,
      exceptionTranslationFilter,
      filterSecurityInterceptor" />
  </security:filter-chain-map>
</bean>

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

 

LogoutFilter

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

 

<bean id="logoutFilter" class="org.springframework.security 
  .web.authentication.logout.LogoutFilter">
  <!-- the post-logout destination -->
  <constructor-arg value="/"/>
    <constructor-arg>
      <array>
        <ref local="logoutHandler"/>
      </array>
    </constructor-arg>
  <property name="filterProcessesUrl" value="/logout"/>
</bean>

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

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

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

 

<bean id="logoutHandler" class="org.springframework.security 
  .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。首先让我们看一下这个过滤器:

 

<bean id="rememberMeAuthenticationFilter" 
  class="org.springframework.security.web 
  .authentication.rememberme.RememberMeAuthenticationFilter">
  <property name="rememberMeServices" ref="rememberMeServices"/>
  <property name="authenticationManager"  ref="customAuthenticationManager" />
</bean>

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

 

<bean id="rememberMeServices" 
  class="org.springframework.security.web.authentication 
  .rememberme.PersistentTokenBasedRememberMeServices">
  <property name="key" value="jbcpPetStore"/>
  <property name="tokenValiditySeconds" value="3600"/>
  <property name="tokenRepository" ref="jdbcRememberMeTokenRepository"/>
  <property name="userDetailsService" ref="jdbcUserService"/>
</bean>

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

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

 

<bean id="jdbcRememberMeTokenRepository" 
  class="org.springframework.security.web 
  .authentication.rememberme.JdbcTokenRepositoryImpl">
  <property name="dataSource" ref="dataSource"/>
</bean>

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

 

<bean id="rememberMeAuthenticationProvider" 
  class="org.springframework.security .authentication.RememberMeAuthenticationProvider">
  <property name="key" value="jbcpPetStore"/>
</bean>

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

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

 

<bean id="customAuthenticationManager" 
  class="org.springframework.security .authentication.ProviderManager">
  <property name="providers">
    <list>
      <ref local="daoAuthenticationProvider"/>
      <ref local=”anonymousAuthenticationProvider”/>
      <ref local="rememberMeAuthenticationProvider"/>
    </list>
  </property>
</bean>

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

 

<bean id="usernamePasswordAuthenticationFilter" 
  class="org.springframework.security.web 
  .authentication.UsernamePasswordAuthenticationFilter">
  <property name="authenticationManager" 
  ref="customAuthenticationManager"/>
  <property name="rememberMeServices" ref="rememberMeServices"/>
</bean>

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

 

<bean id="logoutFilter" 
  class="org.springframework.security.web .authentication.logout.LogoutFilter">
  <constructor-arg value="/"/>
  <constructor-arg>
    <array>
      <ref local="logoutHandler"/>
      <ref local="rememberMeServices"/>
    </array>
  </constructor-arg>
  <property name="filterProcessesUrl" value="/logout"/>
</bean>

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

ExceptionTranslationFilter

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

 

<bean id="exceptionTranslationFilter" 
  class="org.springframework.security.web .access.ExceptionTranslationFilter">
  <property name="authenticationEntryPoint" ref="authenticationEntryPoint"/>
  <property name="accessDeniedHandler" ref="accessDeniedHandler"/>
</bean>

 支持bean的声明如下:

 

<bean id="authenticationEntryPoint" 
  class="org.springframework.security.web 
  .authentication.LoginUrlAuthenticationEntryPoint">
  <property name="loginFormUrl" value="/login.do"/>
</bean>
<bean id="accessDeniedHandler" 
  class="org.springframework.security.web .access.AccessDeniedHandlerImpl">
  <property name="errorPage" value="/accessDenied.do"/>
</bean>

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

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

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

 

<bean class="org.springframework.security 
  .web.access.expression.DefaultWebSecurityExpressionHandler" 
  id="expressionHandler"/>

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

 

<bean class="org.springframework.security.web.access 
  .expression.WebExpressionVoter" id="expressionVoter">
  <property name="expressionHandler" ref="expressionHandler"/>
</bean>

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

 

<bean  class="org.springframework.security.access.vote.AffirmativeBased" 
id="affirmativeBased">
  <property name="decisionVoters">
    <list>
      <ref bean="expressionVoter"/>
    </list>
  </property>
</bean>

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

基于bean配置方法安全

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

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

包装明确的配置

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

l  security命名空间的配置文件为web.xml引用的dogstore-base.xmldogstore-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 serviceREST认证以及用户认证时用到;

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

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

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

 

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

4
0
分享到:
评论
1 楼 xiejx618 2012-03-31  
我不会 明确配置SpEL表达式和投票器 这一部分,不使用use-expressions="true",启动tomcat即报错:
Caused by: java.lang.IllegalArgumentException: Unsupported configuration attributes: [permitAll, hasRole('ROLE_USER')]

不知各位的经验如何,我去看源码时,发现做了 明确配置SpEL表达式和投票器 还是设置了use-expressions="true",这样不是与文章的意思差远了~~~

相关推荐

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

    bean配置跑spring security(mysql数据库)_spring security例子 博客:blog.csdn.net/dsundsun

    SpringSecurity.zip

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

    Spring Security、Spring Social 、Spring Security OAuth

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

    spring security 参考手册中文版

    第六部分 其他主题 209 27.域对象安全(ACL) 209 27.1概述 209 27.2重要概念 211 27.3入门 214 28.预认证方案 216 28.1预认证框架类 216 28.1.1 AbstractPreAuthenticatedProcessingFilter 217 J2...

    Spring Security-3.0.1中文官方文档(翻译版)

    Spring Security-3.0.1 中文官方文档(翻译版) 这次发布的Spring Security-3.0.1 是一个bug fix 版,主要是对3.0 中存在的一些问题进 行修 正。文档中没有添加新功能的介绍,但是将之前拼写错误的一些类名进行...

    Spring攻略PDF版

     第6章 Spring 2.x AOP和AspectJ支持  第二部分 基础主题  第7章 Spring对JDBC的支持   第8章 Spring中的事务管理   第9章 Spring对ORM的支持   第10章 Spring MVC框架   第11章 整合Spring...

    thymeleaf-extras-springsecurity-3.0-master.zip

    This module provides a new dialect called org.thymeleaf.extras.springsecurity3.dialect.SpringSecurityDialect or org.thymeleaf.extras.springsecurity4.dialect.SpringSecurityDialect (depending on the ...

    Spring攻略中文版PDF

     第6章 Spring 2.x AOP和AspectJ支持  第二部分 基础主题  第7章 Spring对JDBC的支持   第8章 Spring中的事务管理   第9章 Spring对ORM的支持   第10章 Spring MVC框架   第11章 整合Spring...

    SpringSecurity 3.0.1.RELEASE.CHM

    Spring Bean配置 18.4.6. LDAP属性和自定义UserDetails 19. JSP标签库 19.1. 声明Taglib 19.2. authorize标签 19.3. authentication 标签 19.4. accesscontrollist 标签 20. Java认证和授权服务(JAAS)供应...

    Spring攻略英文版(附带源码)

     第6章 Spring 2.x AOP和AspectJ支持  第二部分 基础主题  第7章 Spring对JDBC的支持   第8章 Spring中的事务管理   第9章 Spring对ORM的支持   第10章 Spring MVC框架   第11章 整合Spring与其他...

    SpringSecurity实战教程.txt

    Spring Security是一个能够为基于Spring的企业应用系统提供声明式的安全访问控制解决方案的安全框架。它提供了一组可以在Spring应用上下文中配置的Bean,充分利用了Spring IoC,DI(控制反转Inversion of Control ,...

    Spring Security

    Spring Security是一个能够为基于Spring的企业应用系统提供声明式的安全访问控制解决方案的安全框架。它提供了一组可以在Spring应用上下文中配置的Bean,充分利用了Spring IoC,DI(控制反转Inversion of Control ,...

    Spring Security详细介绍及使用含完整代码(值得珍藏)

    Spring Security是一个功能强大且高度可定制的安全框架,专为基于Spring的企业应用系统提供声明式的安全访问控制解决方案。该框架充分利用了Spring IoC、DI(依赖注入)和AOP(面向切面编程)等核心功能,通过一组可...

    spring security3配置和使用

    该项目的历史,然后看看如何开始在程序中使用框架。特别是,我们将看看命名控件配置提供了一个更加简单的方式,在使用传统的spring bean配置时,你不得不实现所有类。 我们也会看看可用的范例程序。

    基于Springboot+Mybatis+ SpringMvc+springsecrity+Redis完整网站后台管理系统

    spring security 全注解式的权限管理 动态配置权限,角色和资源,权限控制到按钮粒度 采用token进行权限校验,禁用session,未登录返回401,权限不足返回403 采用redis存储token及权限信息 内置功能: 用户管理...

    Spring Security 中文教程.pdf

    Spring Bean配置 19.4.6. LDAP属性和自定义UserDetails 20. JSP标签库 20.1. 声明Taglib 20.2. authorize 标签 20.3. authentication 标签 20.4. accesscontrollist 标签 21. Java认证和授权服务...

    spring-boot整合security和mybatis-plus代码

    Spring Security是一个能够为基于Spring的企业应用系统提供声明式的安全访问控制解决方案的安全框架。它提供了一组可以在Spring应用上下文中配置的Bean。

    spring-security-4.2.5.RELEASE-source.zip

    Spring Security 4.2.5是一个能够为基于Spring的企业应用系统提供声明式的安全访问控制解决方案的安全框架。它提供了一组可以在Spring应用上下文中配置的Bean,充分利用了Spring IoC,DI(控制反转Inversion of ...

    基于SpringBoot,Spring Security,JWT,Vue & Element 的前后端分离权限管理系统.zip

    3.自动配置:SpringBoot的自动配置特性利用了Spring对条件化配置的支持,合理地推测应用所需的bean并自动化配置他们。 4.使部署变得简单,SpringBoot内置了三种Servlet容器,Tomcat,Jetty,undertow.我们只需要一个...

    SPRINGSECURITY应用案例

    SPRINGSECURITY 3.2 在WEB应用中的案例源码, 1.如何改造登陆验证 2.如何使用数据库中配置的资源权限信息进行访问控制 3.如何控制对SPRINGBEAN中的类方法的控制

Global site tag (gtag.js) - Google Analytics