Spring WebFlow + Spring Security:使用表达式而不是角色

时间:2015-04-23 15:54:54

标签: java spring spring-security spring-webflow

我创建了一个CustomWebSecurityExpressionHandler,通过搜索函数id来检查db表上的用户。我想在每个函数上更改我的角色,只需要一些db更新和重新启动上下文,而无需重新编译和编辑大量的XML。

我想在Webflow中使用SpringSecurityExpression!就像我可以在Spring的任何其他部分做的那样......

<?xml version="1.0" encoding="UTF-8"?>
<flow xmlns="http://www.springframework.org/schema/webflow"
    xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
    xsi:schemaLocation="http://www.springframework.org/schema/webflow
                          http://www.springframework.org/schema/webflow/spring-webflow-2.0.xsd">

    <secured attributes="isFUUU('key')" />

    <view-state id="main" view="dashboard/main.html" >
    </view-state>

</flow>

如何使isFUU(“key”)正常工作?这是一个自定义的CustomAccessDecisionManager吗?

2 个答案:

答案 0 :(得分:1)

我找到了解决方法

我不得不调试20类spring安全性和webflow来发现在SecurityFlowExecutionListener中,即使你设置spring security来处理表达式,监听器也只是基于角色的。 我发现,对于解析表达式,需要特定类型的配置属性,WebExpressionConfigAttribute才是精确的。 但它不是公共课! https://jira.spring.io/browse/SEC-1727。 所以在这个OLD Jira中,我需要在同一个包中创建我的CustomSecurityFlowExecutionListener(org.springframework.security.web.access.expression)

这里的例子是

CustomSecurityFlowExecutionListener:

package org.springframework.security.web.access.expression; //First part of the trick!

import foo.bar.example.services.security.CustomAccessDecisionManager; 

import java.util.ArrayList;
import java.util.Collection;
import java.util.List;

import org.springframework.expression.ExpressionParser;
import org.springframework.security.access.AccessDecisionManager;
import org.springframework.security.access.ConfigAttribute;
import org.springframework.security.access.SecurityConfig;
import org.springframework.webflow.security.SecurityFlowExecutionListener;
import org.springframework.webflow.security.SecurityRule;

/**
 * Force Spring WebFlow Security listener to use expression!
 * 
 * @author roberto.gabrieli
 */
public class CustomSecurityFlowExecutionListener<T > extends SecurityFlowExecutionListener
{

    /**
     * Convert SecurityRule into a form understood by Spring Security Force the usage of WebExpressionConfigAttribute!
     * 
     * @param rule
     *            the rule to convert
     * @return list of ConfigAttributes for Spring Security
     */
    @Override
    @SuppressWarnings("deprecation")
    protected Collection<ConfigAttribute> getConfigAttributes(SecurityRule rule)
    {
        // Get Access Decision Manager to find if has my expression handler
        AccessDecisionManager adm = getAccessDecisionManager();

        ExpressionParser ep = null;
        //  Check if is my CustomAccessDecisionManager so I can use my expressions
        if ( adm instanceof CustomAccessDecisionManager )
        {
            ep = ((CustomAccessDecisionManager) adm).getWebSecurityExpressionHandler().getExpressionParser();
        }

        List<ConfigAttribute> configAttributes = new ArrayList<ConfigAttribute>();
        for ( String attribute : rule.getAttributes() )
        {
            if ( ep != null )
                // this will end the trick with fireworks!
                configAttributes.add(new WebExpressionConfigAttribute(ep.parseExpression(attribute)));
            else
                configAttributes.add(new SecurityConfig(attribute));
        }
        return configAttributes;
    }
}

的Webflow-config.xml中

<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
    xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:aop="http://www.springframework.org/schema/aop"
    xmlns:context="http://www.springframework.org/schema/context"
    xmlns:util="http://www.springframework.org/schema/util" xmlns:webflow="http://www.springframework.org/schema/webflow-config"
    xmlns:mvc="http://www.springframework.org/schema/mvc"
    xsi:schemaLocation="http://www.springframework.org/schema/aop http://www.springframework.org/schema/aop/spring-aop-4.1.xsd
        http://www.springframework.org/schema/webflow-config http://www.springframework.org/schema/webflow-config/spring-webflow-config-2.4.xsd
        http://www.springframework.org/schema/mvc http://www.springframework.org/schema/mvc/spring-mvc-4.1.xsd
        http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans-4.1.xsd
        http://www.springframework.org/schema/util http://www.springframework.org/schema/util/spring-util-4.1.xsd
        http://www.springframework.org/schema/context http://www.springframework.org/schema/context/spring-context-4.1.xsd">
... 

    <bean id="securityFlowExecutionListener"
        class="org.springframework.security.web.access.expression.MamSecurityFlowExecutionListener">
        <property name="accessDecisionManager" ref="customAccessDecisionManager"/>
    </bean>

...
</beans>

答案 1 :(得分:0)

我找到了另一种解决方案,如何在WebFlows中使用Spring Expression Language。它来自“Pro Spring Security”一书。简而言之,他们使用自定义AccessDecisionMangerAccessDecisionVoter)和自定义implements AccessDesisionVoter<org.springframework.webflow.engine.State定义自定义SecurityExpressionRoot。因此,无需像解决方案那样拥有自己的监听器。这些自定义类支持流状态级别的表达式。您可以使用此link在github上找到完整的示例。