如何以编程方式配置过滤器链?

How to configure the filter chain programmatically?

有没有一种方法可以根据上述 users roleuser 对特定 [URL] 的访问进行编程限制。

例如,在 shiro.ini 文件中,您可以定义:

      [urls]
      ...
  1.  /app/**= user

这可以在代码中定义一个 filter chain 来实现:

 .....

 UserFilter user = new UserFilter();//create user filter
 user.setLoginUrl("login.xhtml");


FilterChainManager fcMan = new DefaultFilterChainManager();
fcMan.addFilter("user", user);//add filter to filter chain
fcMan.createChain("/app/**", "user");//define url path expression for filterName

.....

我的问题是如何使用 roles 实现这一点,就像我在 shiro.ini 文件中所做的那样:

[urls]
...
/api/admin/**= user, roles[admin]
...

例如:

RolesAuthorizationFilter adminRole = new RolesAuthorizationFilter();//eg create role filter      
adminRole.setLoginUrl("login.xhtml");
UserFilter user = new UserFilter();//create user filter
user.setLoginUrl("login.xhtml");


FilterChainManager fcMan = new DefaultFilterChainManager();

fcMan.addFilter("user", user);
fcMan.addFilter("admin", adminRole);      
fcMan.createChain("/api/admin/**", "admin");

我是《Pairing Apache Shiro and Java EE 7》一书的作者,您可以免费获取这本书 here

在本书中,我以编程方式编写了所有 Shiro 组件,不需要 shiro.ini 文件。

我使用 CDI 事件生成 FilterChainResolver:

@Produces
public FilterChainResolver getFilterChainResolver() {
    FilterChainResolver filterChainResolver = null;
    if (filterChainResolver == null) {
        FormAuthenticationFilter authc = new FormAuthenticationFilter();
        AnonymousFilter anon = new AnonymousFilter();
        UserFilter user = new UserFilter();

        authc.setLoginUrl(WebPages.LOGIN_URL);
        user.setLoginUrl(WebPages.LOGIN_URL);

        FilterChainManager fcMan = new DefaultFilterChainManager();
        fcMan.addFilter("authc", authc);
        fcMan.addFilter("anon", anon);
        fcMan.addFilter("user", user);

        fcMan.createChain("/index.html", "anon");
        fcMan.createChain("/css/**", "anon");
        fcMan.createChain("/api/**", "anon");
        fcMan.createChain(WebPages.LOGIN_URL, "authc");
        fcMan.createChain("/**", "user");

        PathMatchingFilterChainResolver resolver = new PathMatchingFilterChainResolver();
        resolver.setFilterChainManager(fcMan);
        filterChainResolver = resolver;
    }
    return filterChainResolver;
}

接下来,我们在 :

中注入 FilterChainResolver
@WebListener
public class ShiroListener extends EnvironmentLoaderListener {

    @Inject
    WebSecurityManager securityManager;

    @Inject
    FilterChainResolver filterChainResolver;

    @Override
    protected WebEnvironment createEnvironment(ServletContext sc) {
        DefaultWebEnvironment webEnvironment = (DefaultWebEnvironment) super.createEnvironment(sc);

        webEnvironment.setSecurityManager(securityManager);
        webEnvironment.setFilterChainResolver(filterChainResolver);

        return webEnvironment;
    }
    ...
}

现在,应用了 FilterChainResolver,一切都会如愿以偿。