【问题标题】:How to apply spring boot filter based on URL pattern?如何基于 URL 模式应用 Spring Boot 过滤器?
【发布时间】:2017-02-04 06:01:30
【问题描述】:

我创建了一个 Spring Boot 过滤器 - 使用 @Component 注释实现 GenericFilterBean

@Component 
public class MyAuthenticationFilter  extends GenericFilterBean {
...
@Override
public void doFilter(ServletRequest servletRequest, ServletResponse servletResponse, FilterChain filterChain) throws IOException, ServletException {
...
}
}

过滤器由 Spring Boot Framework 自动识别,适用于所有 REST API。我希望此过滤器仅适用于某个 URL 路径,例如 /api/secure/*,但我找不到正确的方法。 我试过@WebFilter,但没用。 我没有使用 XML 配置或 servlet 初始化程序 - 只是注释。

什么是让它工作的正确方法?

【问题讨论】:

    标签: java spring filter spring-boot annotations


    【解决方案1】:

    @user1283002 我认为可以使用@WebFilter。我只是偶然发现了这个article。根据文章(我自己没试过):

    @WebFilter(urlPatterns = "/api/count")
    public class ExampleFilter implements Filter{
        // ..........
    }
    
    // and let Spring know to scan to find such @WebFilter annotation in your config
    // class by using the @ServletComponentScan annotation like
    
    @ServletComponentScan
    @SpringBootApplication
    public class MyApplication extends SpringBootServletInitializer {
    
        public static void main(String[] args) throws Exception {
            SpringApplication.run(MyApplication.class, args);
        }
    
       // ..........
    
    }
    

    编辑: 在进一步阅读 @ServletComponentScan 的文档后,我发现了一个有趣的免责声明

    仅在使用嵌入式网络服务器时执行扫描

    这意味着在 Web 容器(例如:Apache Tomcat)中部署我们的应用程序时,Spring 框架不会扫描此类,因此不会应用其上的任何 spring 配置(如果有)。

    如果没有要进行的 Spring 配置,你可以不用做任何进一步的更改,如果不是,只需将 @Component 扫描添加到过滤器并确保它的包位于你的 @ComponentScan 注释。

    【讨论】:

      【解决方案2】:

      如果您能够扩展OncePerRequestFilter,还有另一种选择。例如:

      public class SomeFilter extends OncePerRequestFilter {
      
          @Override
          protected void doFilterInternal(HttpServletRequest request, HttpServletResponse response, FilterChain filterChain) throws ServletException, IOException {
              // your filter logic ....
          }
      
          @Override
          protected boolean shouldNotFilter(HttpServletRequest request) {
              String path = request.getServletPath();
              return !path.startsWith("/api/secure/");
          }
      }
      

      【讨论】:

      • 这正是我想要的。泰
      【解决方案3】:

      您可以像这样添加过滤器:

      @Bean
      public FilterRegistrationBean someFilterRegistration() {
      
          FilterRegistrationBean registration = new FilterRegistrationBean();
          registration.setFilter(someFilter());
          registration.addUrlPatterns("/url/*");
          registration.addInitParameter("paramName", "paramValue");
          registration.setName("someFilter");
          registration.setOrder(1);
          return registration;
      } 
      
      @Bean(name = "someFilter")
      public Filter someFilter() {
          return new SomeFilter();
      }
      

      【讨论】:

      • 我仍然很奇怪为什么它不能通过像@WebFilter 这样的注释来解决,但这对我来说非常有效。谢谢!
      • 可以通过注解来实现吗?
      猜你喜欢
      • 2021-10-29
      • 2015-04-02
      • 2016-08-24
      • 2017-06-09
      • 2020-08-11
      • 2018-07-17
      • 2015-05-26
      • 2013-06-16
      • 2015-09-06
      相关资源
      最近更新 更多