2009-06-12 271 views
28

在迁移遗留应用程序的Spring Security我有以下异常:如何在Spring Security中使用自定义角色/权限?

org.springframework.beans.factory.BeanCreationException: Error creating bean with name '_filterChainProxy': Initialization of bean failed; nested exception is org.springframework.beans.factory.BeanCreationException: Error creating bean with name '_filterChainList': Cannot resolve reference to bean '_filterSecurityInterceptor' while setting bean property 'filters' with key [3]; nested exception is org.springframework.beans.factory.BeanCreationException: Error creating bean with name '_filterSecurityInterceptor': Invocation of init method failed; nested exception is java.lang.IllegalArgumentException: Unsupported configuration attributes: [superadmin] 
at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.doCreateBean(AbstractAutowireCapableBeanFactory.java:480) 
at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory$1.run(AbstractAutowireCapableBeanFactory.java:409) 
at java.security.AccessController.doPrivileged(Native Method) 
at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.createBean(AbstractAutowireCapableBeanFactory.java:380) 
at org.springframework.beans.factory.support.AbstractBeanFactory$1.getObject(AbstractBeanFactory.java:264) 

在旧的应用程序有像“超级管理员”,“编辑”,“服务支持”等,但在所有的Spring Security例子角色我只看到像“ROLE_”(“ROLE_ADMIN”等)的角色。当我将“superadmin”重命名为“ROLE_ADMIN”并仅在配置中使用此角色时,一切正常。

不起作用:

<http auto-config="true">          
    <intercept-url pattern="/restricted/**" access="superadmin"/> 
    <form-login 
     authentication-failure-url="/secure/loginAdmin.do?error=true" 
     login-page="/secure/loginAdmin.do" />   
</http> 

作品:

<http auto-config="true">          
    <intercept-url pattern="/restricted/**" access="ROLE_ADMIN"/> 
    <form-login 
     authentication-failure-url="/secure/loginAdmin.do?error=true" 
     login-page="/secure/loginAdmin.do" />   
</http> 

可以使用自定义角色的名字呢?

+0

这个[问题](http://stackoverflow.com/questions/283870/acegi-security-how-do-i-add - 另一个授权 - 认证 - 匿名)可能会有所帮助。 – kgiannakakis 2009-06-12 14:29:31

回答

39

您正在使用预期角色以"ROLE_"前缀开头的默认配置。您将不得不添加自定义安全配置并将rolePrefix设置为“”;

http://forum.springsource.org/archive/index.php/t-53485.html

+0

我可以有ROLE_FOO或ROLE_BAR或ROLE_ANYTHING_I_WANT吗?你提供的链接并没有解决问题,它只是一些人说“无法为RoleVoter设置RolePrefix” – 2009-11-05 13:28:45

11

下面是使用访问表达式完整的配置(由@rodrigoap提供的链接似乎有点有点过时):

<http 
     access-decision-manager-ref="accessDecisionManager" 
     use-expressions="true"> 

<beans:bean id="accessDecisionManager" class="org.springframework.security.access.vote.AffirmativeBased"> 
    <beans:property name="decisionVoters"> 
     <beans:list> 
      <beans:bean class="org.springframework.security.web.access.expression.WebExpressionVoter"/> 
      <beans:bean class="org.springframework.security.access.vote.RoleVoter"> 
       <beans:property name="rolePrefix" value=""/> 
      </beans:bean> 
      <beans:bean class="org.springframework.security.access.vote.AuthenticatedVoter"/> 
     </beans:list> 
    </beans:property> 
</beans:bean> 
7

您也可以始终使用表达式(通过config use-expressions="true")忽略ROLE_前缀。

阅读的Spring Security 3.1的源代码后,我发现当use-expressions="true"

对于<security:http >
HttpConfigurationBuilder#createFilterSecurityInterceptor()将REGIST WebExpressionVoter但不RoleVoterAuthenticatedVoter;

<security:global-method-security >对于:GlobalMethodSecurityBeanDefinitionParser#registerAccessManager()将REGIST PreInvocationAuthorizationAdviceVoter(有条件地),则总是记数RoleVoterAuthenticatedVoter,记数Jsr250Voter有条件;

PreInvocationAuthorizationAdviceVoter将处理PreInvocationAttribute(PreInvocationExpressionAttribute将用作执行),它是根据@PreAuthorize生成的。 PreInvocationExpressionAttribute#getAttribute()总是返回null,所以RoleVoter,AuthenticatedVoter不投票。

2

使用 Spring Security 3.2,这为我工作。

更改角色前缀:

<beans:bean id="roleVoter" class="org.springframework.security.access.vote.RoleVoter"> 
    <beans:property name="rolePrefix" value="NEW_PREFIX_"/> 
</beans:bean> 

<beans:bean id="authenticatedVoter" class="org.springframework.security.access.vote.AuthenticatedVoter"/> 

<beans:bean id="accessDecisionManager" class="org.springframework.security.access.vote.AffirmativeBased"> 
    <beans:constructor-arg > 
     <beans:list> 
      <beans:ref bean="roleVoter"/> 
      <beans:ref bean="authenticatedVoter"/> 
     </beans:list> 
    </beans:constructor-arg> 
</beans:bean> 

根据要应用它可以在安全模式级或豆级应用中的作用前缀。

<http access-decision-manager-ref="accessDecisionManager" use-expressions="true"> 

在服务级别应用的角色前缀:

<beans:bean id="myService" class="com.security.test"> 
    <security:intercept-methods access-decision-manager-ref="accessDecisionManager"> 
     <security:protect access="NEW_PREFIX_ADMIN"/> 
    </security:intercept-methods> 
</beans:bean> 
相关问题