SpringBoot集成Feign部署OpenShift新增过滤器后Pod反复重启问题求助
问题排查结论
根本原因
你遇到的Pod反复重启问题和Feign Client本身没有直接关联,是新增的全局过滤器和OpenShift的健康检查机制冲突导致:
- 你新增的
CheckFilter加了@Component注解,会被Spring Boot自动注册为全局过滤器,拦截所有进入服务的HTTP请求,默认要求请求必须携带包含check.com的Referer头,否则直接返回401未授权。 - OpenShift部署环境默认会配置存活探针、就绪探针,定期发起请求检测Pod运行状态,这类集群内部发起的探针请求不会携带Referer头,会被过滤器直接拦截返回401。
- OpenShift检测到探针连续失败后,会判定Pod不健康,强制销毁并重启Pod,你提供的日志显示服务启动成功后收到第一个请求就触发了上下文关闭,完全匹配该流程的特征。
- 补充:如果集群内有其他服务通过Feign Client调用当前服务接口,Feign默认发起的请求也不会携带Referer头,同样会被拦截,可能进一步触发服务调用失败、熔断器打开的问题。
修复方案
方案1:过滤器放行健康检查路径(优先推荐)
先确认OpenShift配置的探针路径,Spring Boot项目通常使用Actuator的健康检查端点/actuator/health(1.x版本为/health),修改过滤器逻辑,对探针路径直接放行:
@Override public void doFilter(ServletRequest request, ServletResponse response, FilterChain chain) throws IOException, ServletException { HttpServletRequest httpRequest = (HttpServletRequest) request; HttpServletResponse httpResponse = (HttpServletResponse) response; String requestUri = httpRequest.getRequestURI(); // 放行健康检查路径,可根据实际配置调整 if (requestUri.startsWith("/actuator/health") || requestUri.startsWith("/health")) { chain.doFilter(request, response); return; } String referer = httpRequest.getHeader(HttpHeaders.REFERER); if (StringUtils.isNotBlank(referer) && referer.contains(CHECK_DOMAIN)) { chain.doFilter(request, response); } else { httpResponse.sendError(HttpServletResponse.SC_UNAUTHORIZED); } }
方案2:配置过滤器仅拦截指定业务路径
如果Referer校验只需要针对对外暴露的业务接口,可以取消过滤器的全局注册:去掉CheckFilter类上的@Component注解,通过FilterRegistrationBean手动注册,指定需要拦截的路径:
@Configuration public class FilterConfig { @Bean public FilterRegistrationBean<CheckFilter> checkFilterRegistration() { FilterRegistrationBean<CheckFilter> registration = new FilterRegistrationBean<>(); registration.setFilter(new CheckFilter()); // 仅拦截需要校验的业务路径,比如所有/api开头的接口 registration.addUrlPatterns("/api/*"); registration.setName("checkFilter"); registration.setOrder(1); return registration; } }
方案3:放行内部Feign调用请求(适用于有内部服务调用的场景)
如果存在集群内部服务通过Feign调用当前服务的场景,可以给Feign请求统一添加内部标识头,过滤器识别后直接放行:
- 新增Feign请求拦截器,给所有Feign调用添加标识头:
@Component public class FeignInternalInterceptor implements RequestInterceptor { @Override public void apply(RequestTemplate template) { template.header("X-Internal-Service-Call", "true"); } }
- 在
CheckFilter中添加对应放行逻辑:
String internalCallFlag = httpRequest.getHeader("X-Internal-Service-Call"); if ("true".equals(internalCallFlag)) { chain.doFilter(request, response); return; }
内容的提问来源于stack exchange,提问作者Abhiram Tilak Veerapaneni
相关产品推荐
相关产品推荐

