2016-07-19 13 views
0

SpringアプリケーションでWebFilterを追加しようとしています。しかし、私は.xmlファイルを使用していません(私のアプリケーションはそれを必要としないのでweb.xmlでさえありません)。私は/test/*パターンに一致する要求だけがフィルタリングされることを期待していSpring WebFilter Mapping

@WebFilter("/test/*") 
public class RequestFilter implements Filter { 

@Override 
public void init(FilterConfig filterConfig) throws ServletException { } 

@Override 
public void doFilter(ServletRequest request, ServletResponse response, FilterChain chain) 
     throws IOException, ServletException { } 

@Override 
public void destroy() { } 

、しかし:

@Override 
protected Filter[] getServletFilters() { 
    return new Filter[]{new RequestFilter()}; 
} 

そして、私のRequestFilter.javaを:

だから、私はAbstractAnnotationConfigDispatcherServletInitializerを拡張し、私のクラスに追加しました任意のリソースへの要求がフィルタリングされます。

どのようにフィルタをマッピングできますか?

ありがとうございました。

答えて

0

@WebFilter - 春の注釈ではありません。 Springはそれを無視します。メソッドgetServletFiltersは、フィルタの配列をURLにマッピングせずに返します。そこで彼らはすべての要求に対してトリガーをかけました。 web.xmlにurl-mappingを書きたくない場合は、Filterの代わりにHandlerInterceptorを使用できます。彼らはDispatcherServletInitializerでプログラムマップすることができます。

public class SomeInterceptor extends HandlerInterceptorAdapter { 
    @Override 
    public boolean preHandle(HttpServletRequest request, HttpServletResponse response, Object handler) 
     throws Exception { 
     // ... 
     return true; 
    } 
} 

@Configuration 
@ComponentScan("com.example") 
@EnableWebMvc 
public class AppConfig extends WebMvcConfigurerAdapter { 
    @Override 
    public void addInterceptors(InterceptorRegistry registry) { 
     registry 
      .addInterceptor(new SomeInterceptor()) 
      .addPathPatterns("/test/*"); 
    } 
} 

public class WebAppInitializer implements WebApplicationInitializer { 
    public void onStartup(ServletContext servletContext) throws ServletException { 
     AnnotationConfigWebApplicationContext ctx = new AnnotationConfigWebApplicationContext(); 
     ctx.register(AppConfig.class); 
     ctx.setServletContext(servletContext);  
     Dynamic dynamic = servletContext.addServlet("dispatcher", new DispatcherServlet(ctx)); 
     dynamic.addMapping("/"); 
     dynamic.setLoadOnStartup(1); 
    } 
} 

それとも、あなた自身のWebFilterアノテーションを定義することができます!

public class GlobMatcher { 
    public static boolean match(String pattern, String text) { 
     String rest = null; 
     int pos = pattern.indexOf('*'); 
     if (pos != -1) { 
      rest = pattern.substring(pos + 1); 
      pattern = pattern.substring(0, pos); 
     } 

     if (pattern.length() > text.length()) 
      return false; 

     for (int i = 0; i < pattern.length(); i++) 
      if (pattern.charAt(i) != '?' 
        && !pattern.substring(i, i + 1).equalsIgnoreCase(text.substring(i, i + 1))) 
       return false; 

     if (rest == null) { 
      return pattern.length() == text.length(); 
     } else { 
      for (int i = pattern.length(); i <= text.length(); i++) { 
       if (match(rest, text.substring(i))) 
        return true; 
      } 
      return false; 
     } 
    } 
} 

注釈自体::URLパターンマッチングの

@Retention(RetentionPolicy.RUNTIME) 
@Target(ElementType.TYPE) 
public @interface WebFilter { 
    String[] urlPatterns(); 
} 

パススルー機能:

@Aspect 
public class WebFilterMatcher { 
    @Pointcut("within(@com.example.WebFilter *)") 
    public void beanAnnotatedWithWebFilter() {} 

    @Pointcut("execution(boolean com.example..preHandle(..))") 
    public void preHandleMethod() {} 

    @Pointcut("preHandleMethod() && beanAnnotatedWithWebFilter()") 
    public void preHandleMethodInsideAClassMarkedWithWebFilter() {} 

    @Around("preHandleMethodInsideAClassMarkedWithWebFilter()") 
    public Object beforeFilter(ProceedingJoinPoint joinPoint) throws Throwable { 
     Object[] args = joinPoint.getArgs(); 
     if(args.length > 0) { 
      HttpServletRequest request = (HttpServletRequest) args[0]; 
      Class target = joinPoint.getTarget().getClass(); 
      if (target.isAnnotationPresent(WebFilter.class)) { 
       String[] patterns = ((WebFilter) target.getAnnotation(WebFilter.class)).urlPatterns(); 
       for (String pattern : patterns) { 
        if (GlobMatcher.match(pattern, request.getRequestURI())) { 
         return joinPoint.proceed(); 
        } 
       } 
      } 
     } 
     return true; 
    } 
} 

インターセプタまず、あなたはURLパターンに一致するためのユーティリティクラスが必要で

@WebFilter(urlPatterns = {"/test/*"}) 
public class SomeInterceptor extends HandlerInterceptorAdapter { 
    @Override 
    public boolean preHandle(HttpServletRequest request, HttpServletResponse response, Object handler) throws Exception { 
     // ... 
     return true; 
    } 
} 

し、コンテキストコンフィギュレーションにはほとんど変化:

<beans> <!-- Namespaces are omitted for brevity --> 
    <aop:aspectj-autoproxy /> 

    <bean id="webFilterMatcher" class="com.example.WebFilterMatcher" /> 

    <mvc:interceptors> 
    <bean class="com.example.SomeInterceptor" /> 
    </mvc:interceptors> 
</beans> 
+0

おかげで、セルゲイ。私はこのスレッドを完全に忘れてしまった。しかし、結局、私はインターセプタを使用しました。登録を行うだけで、春のセキュリティを使用している場合は、HttpSecurityオブジェクトに含まれるSecurityFilterChainによってフィルタを含めることもできます。 –