北屋教程网

专注编程知识分享,从入门到精通的编程学习平台

Spring Boot 内置的7个Filter,太强了

1. 简介

在项目开发中,Filter(过滤器)是Servlet规范中的一项重要技术,充当请求与响应的"守门人"。它允许开发者在请求到达目标资源(如Controller, Servlet)之前或响应返回客户端之前,对请求和响应进行预处理与后处理。

核心功能:

  • 请求拦截:如校验用户身份、设置字符编码、记录日志等。
  • 响应修改:如压缩响应内容、添加自定义响应头。

应用场景:

  • 安全防护:过滤非法请求,防止SQL注入或XSS攻击。
  • 性能优化:通过缓存或压缩减少网络传输。
  • 统一处理:集中管理跨域请求(CORS)、异常处理等。

Filter#doFilter方法实现链式调用,开发者可灵活组合多个Filter构建处理逻辑,是构建可扩展、可维护Web应用的关键组件。

在 Spring Boot 中,提供了许多实用的内置 Filter,开发者无需再自行编写,借助它们能更高效地构建 Web 应用。接下来,我们将详细介绍Spring Boot提供的非常强大的8个核心Filter。

2. 核心过滤器

2.1 字符编码Filter

CharacterEncodingFilter该过滤器应该不会陌生,这是非常早Spring就提供的一个过滤器,用来设置请求/响应字符编码。

@Bean
CharacterEncodingFilter characterEncodingFilter() {
  CharacterEncodingFilter filter = new CharacterEncodingFilter() ;
  filter.setEncoding("UTF-8");
  filter.setForceRequestEncoding(true);
  filter.setForceResponseEncoding(true);
  return filter ;
}

2.2 请求日志Filter


CommonsRequestLoggingFilter
一个简单的请求日志过滤器,它会将请求 URI(以及可选的查询字符串)写入到 Commons Log(日志)中。

@Bean
CommonsRequestLoggingFilter commonsRequestLoggingFilter() {
  CommonsRequestLoggingFilter filter = new CommonsRequestLoggingFilter() ;
  filter.setIncludeQueryString(true) ;
  filter.setIncludeHeaders(true) ;
  return filter ;
}

该过滤器提供了很多可配置项,如下:

最终效果如下:

注意,你还需要开启debug级别。

logging:
  level:
    '[org.springframework.web.filter]': debug

2.3 跨域Filter

CorsFilter用于处理 CORS 预检请求(pre-flight requests),并通过 CorsProcessor 拦截 CORS 简单请求和实际请求,同时根据通过提供的 CorsConfigurationSource 匹配的策略,更新响应(例如,添加 CORS 响应头)。

@Bean
CorsFilter corsFilter() {
  CorsConfiguration config = new CorsConfiguration();
  config.setAllowCredentials(false);
  config.addAllowedOrigin("*") ;
  config.addAllowedHeader("*") ;
  config.addAllowedMethod("*") ;
  UrlBasedCorsConfigurationSource source = new UrlBasedCorsConfigurationSource();
  source.registerCorsConfiguration("/**", config);
  CorsFilter filter = new CorsFilter(source);
  return filter;
}

2.4 表单数据过滤器

FormContentFilter用于解析 HTTP PUT、PATCH 和 DELETE 请求中的表单数据,并将其暴露为 Servlet 请求参数。默认情况下,Servlet 规范仅要求对 HTTP POST 请求执行此操作。

现在有如下接口:

@PutMapping("/put/param")
public String params(String name, Integer age) {
  return name + "@" + age ;
}

通过postman访问该接口,输出结果如下:

没有获取到数据。接下来,配置如下过滤器

@Bean
FormContentFilter formContentFilter() {
  FormContentFilter filter = new FormContentFilter() ;
  return filter ;
}

再次访问上面的接口

成功获取值。

在Spring Boot中默认是已经注册了该过滤器的一个子类OrderedFormContentFilter

2.5 弥补HTTP方法限制的桥梁

HiddenHttpMethodFilter 该过滤器用于解决浏览器仅支持GET/POST方法的限制,通过解析POST请求中的隐藏字段(如_method),将请求方法转换为PUT、DELETE、PATCH等,使后端可接收标准HTTP方法,助力RESTful API开发。

@Bean
HiddenHttpMethodFilter hiddenHttpMethodFilter() {
  HiddenHttpMethodFilter filter = new HiddenHttpMethodFilter() ;
  // 默认要求传的参数名:_method
  filter.setMethodParam("_cm") ;
  return filter ;
}

测试

定义如下Controller接口请求方法为patch,然后我们用post方式提交。

@PatchMapping("/patch")
public String patch(String name) {
  return name ;
}

成功通过上面配置的过滤器映射到了patch上。该过滤器非常适合解决那些不允许get,post之外method的安全管理环境。

2.6 请求上下文线程绑定助手

RequestContextFilter 将请求上下文(如 Locale、请求属性等)绑定到当前线程,通过 LocaleContextHolder 和 RequestContextHolder 提供访问。

@Bean
RequestContextFilter requestContextFilter() {
  RequestContextFilter filter = new RequestContextFilter() ;
  // 子线程也可以获取上下文对象
  filter.setThreadContextInheritable(true) ;
  return filter ;
}

使用

ServletRequestAttributes attrs = (ServletRequestAttributes) RequestContextHolder.currentRequestAttributes() ;
HttpServletRequest request = attrs.getRequest() ;

2.7 解析请求路径

ServletRequestPathFilter 该过滤器用来解析并缓存当前请求的路径。

@Bean
ServletRequestPathFilter servletRequestPathFilter() {
  ServletRequestPathFilter filter = new ServletRequestPathFilter() ;
  return filter ;
}

使用

ServletRequestAttributes attrs = (ServletRequestAttributes) RequestContextHolder.currentRequestAttributes() ;
HttpServletRequest request = attrs.getRequest() ;
RequestPath requestPath = ServletRequestPathUtils.getParsedRequestPath(request) ;
// ...

你可以在任何其它bean组件中获取当前请求的完整uri。

控制面板
您好,欢迎到访网站!
  查看权限
网站分类
最新留言