feign异常feign.RetryableException & NoHttpResponseException
系统总是出现feign.RetryableException
,需要找到原因并解决,虽然问题不大,但是一直有这个异常日志。
项目采用的是spring-cloud-starter-openfeign
自动注入、apache httpclient
做连接池。并没有对配置做相关优化,采用默认配置。
feign.RetryableException定位
通过异常栈定位到问题出在feign.SynchronousMethodHandler#invoke
内调用executeAndDecode
。执行请求出现异常后抛出。
1 | public Object invoke(Object[] argv) throws Throwable { |
默认情况下feign
配置重试机制使用的是feign.Retryer.Default
,默认重试5次。
在使用了SpringBoot
自动配置后,在org.springframework.cloud.openfeign.FeignClientsConfiguration#feignRetryer
可以看到默认使用的是feign.Retryer#NEVER_RETRY
,里面是不做重试直接抛出异常。那就可以看到为什么请求失败会出现feign.RetryableException
。
NoHttpResponseException 定位
在上面feign
异常栈的后面可以看到NoHttpResponseException
异常,通过异常栈可以看到代码org.apache.http.impl.conn.DefaultHttpResponseParser#parseHead
处抛出的异常,是读取返回时出错抛出。
从stackoverflow Apache HttpClient Interim Error: NoHttpResponseException里面可以看到,根本原因是因为使用了过期连接导致。
解决办法:
- 官方建议定时清理过期连接。
- 设置自定义重试次数。
- 使用okhttp替换
apache httpclient
。
使用
okhttp
添加配置feign.httpclient.enabled=false
,避免第三方依赖了feign-httpclient
,如果确认没有依赖可以不需要
添加feign.okhttp.enabled=true
启动okhttp