package com.mossle.core.servlet; import java.io.IOException; import java.util.ArrayList; import java.util.List; import javax.servlet.Filter; import javax.servlet.FilterChain; import javax.servlet.FilterConfig; import javax.servlet.ServletException; import javax.servlet.ServletRequest; import javax.servlet.ServletResponse; public class CompositeFilter implements Filter { private List<? extends Filter> filters = new ArrayList<Filter>(); public void setFilters(List<? extends Filter> filters) { this.filters = new ArrayList<Filter>(filters); } public void destroy() { for (int i = filters.size(); i-- > 0;) { Filter filter = filters.get(i); filter.destroy(); } } public void init(FilterConfig config) throws ServletException { for (Filter filter : filters) { filter.init(config); } } public void doFilter(ServletRequest request, ServletResponse response, FilterChain chain) throws IOException, ServletException { new VirtualFilterChain(chain, filters).doFilter(request, response); } private static final class VirtualFilterChain implements FilterChain { private final FilterChain originalChain; private final List<? extends Filter> additionalFilters; private int currentPosition = 0; private VirtualFilterChain(FilterChain chain, List<? extends Filter> additionalFilters) { this.originalChain = chain; this.additionalFilters = additionalFilters; } public void doFilter(final ServletRequest request, final ServletResponse response) throws IOException, ServletException { if (currentPosition == additionalFilters.size()) { originalChain.doFilter(request, response); } else { currentPosition++; Filter nextFilter = additionalFilters.get(currentPosition - 1); nextFilter.doFilter(request, response, this); } } } }