简体   繁体   中英

How to add multiple custom-filter in Spring Security 3?

I need add two custom filters for FORM_LOGIN_FILTER, eg

<custom-filter after="FORM_LOGIN_FILTER" ref="myUsernamePasswordAuthenticationFilter" />
<custom-filter after="FORM_LOGIN_FILTER" ref="myUsernamePasswordAuthenticationFilter2" />

What I expect the filter sequences is:
1. Predefind FORM_LOGIN_FILTER
2. myUsernamePasswordAuthenticationFilter
3. myUsernamePasswordAuthenticationFilter2

But above will cause configuration error. So, anyone knows how to write the right config? Thanks!

Use Spring's CompositeFilter to wrap your custom filters list, and then put that filter on relevant position on SecurityFilterChain .

Eg like this:

<bean id="customFilters" class="org.springframework.web.filter.CompositeFilter">
    <property name="filters">
        <list>
            <ref bean="myUsernamePasswordAuthenticationFilter"/>
            <ref bean="myUsernamePasswordAuthenticationFilter2"/>
        </list>
    </property>
</bean>
...
<custom-filter after="FORM_LOGIN_FILTER" ref="customFilters" />

Do this:

<custom-filter after="FORM_LOGIN_FILTER" ref="myUsernamePasswordAuthenticationFilter" />
<custom-filter before="BASIC_AUTH_FILTER" ref="myUsernamePasswordAuthenticationFilter2" />

That should put them where you want them.

I solved it like this:

public class QmLoginFilterWrapper extends GenericFilterBean implements ApplicationEventPublisherAware,
    MessageSourceAware
{
  private static final Logger                          LOGGER     = LoggerFactory.getLogger(QmLoginFilterWrapper.class);

  private List<AbstractAuthenticationProcessingFilter> filterList = new ArrayList<AbstractAuthenticationProcessingFilter>();

  @Override
  public void doFilter(ServletRequest request, ServletResponse response, final FilterChain chain) throws IOException,
      ServletException
  {
    FilterChain filterChain = new FilterChain() {

      @Override
      public void doFilter(ServletRequest arg0, ServletResponse arg1) throws IOException, ServletException
      {
        chain.doFilter(arg0, arg1);

      }
    };
    Vector<FilterChain> filterChains = new Vector<FilterChain>();
    filterChains.add(filterChain);
    if (LOGGER.isDebugEnabled())
    {
      LOGGER.debug("Filtering {} filters", filterList.size());
    }
    for (final GenericFilterBean filter : filterList)
    {
      final FilterChain lastChain = filterChains.lastElement();
      FilterChain loopChain = new FilterChain() {

        @Override
        public void doFilter(ServletRequest arg0, ServletResponse arg1) throws IOException, ServletException
        {
          if (LOGGER.isDebugEnabled())
          {
            LOGGER.debug("running filter {}", filter.getClass().getName());
          }
          filter.doFilter(arg0, arg1, lastChain);
        }
      };
      filterChains.add(loopChain);
    }
    filterChains.lastElement().doFilter(request, response);
  }

  @Override
  public void setMessageSource(MessageSource messageSource)
  {
    for (MessageSourceAware filter : filterList)
    {
      filter.setMessageSource(messageSource);
    }
  }

  @Override
  public void setApplicationEventPublisher(ApplicationEventPublisher applicationEventPublisher)
  {
    for (ApplicationEventPublisherAware applicationEventPublisherAware : filterList)
    {
      applicationEventPublisherAware.setApplicationEventPublisher(applicationEventPublisher);
    }
  }

  public List<AbstractAuthenticationProcessingFilter> getFilterList()
  {
    return filterList;
  }

  public void setFilterList(List<AbstractAuthenticationProcessingFilter> filterList)
  {
    this.filterList = filterList;
    Collections.reverse(this.filterList);
  }

}

Then in the context XML i have:

  <bean id="qmAuthFilter" class="com.qmplus.common.logon.QmLoginFilterWrapper">
    <property name="filterList">
      <list>
        <ref local="samlProcessingFilter" />
        <ref local="usernamePasswordAuthenticationFilter" />
      </list>
    </property>
  </bean>

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM