关于Feign 中 Hystrix 的使用
关于@FeignClient中参数详情:
https://www.cnblogs.com/moonandstar08/p/7565442.html
Feign 常用配置参考:
https://www.iteye.com/blog/huan1993-2424108
Spring Cloud Feign就是通过Fallback实现的,有两种方式:
1、@FeignClient.fallback = UserFeignFallback.class指定一个实现Feign接口的实现类。
2、@FeignClient.fallbackFactory = UserFeignFactory.class指定一个实现FallbackFactory
因为Fallback是通过Hystrix实现的, 所以需要开启Hystrix,spring boot application.properties文件配置feign.hystrix.enabled=true,这样就开启了Fallback
第一种:
@FeignClient(name = "user",fallback = UserFeignFallback.class)
public interface UserFeign {
@PostMapping
void save(User user);
}
@Component
public class UserFeignFallback implements UserFeign {
@Override
public void save(User user) {
}
}
第一种写法简单,缺点在于获取不到HTTP请求错误状态码和信息
第二种:
@FeignClient(name = "user",fallbackFactory = UserFeignFactory.class)
public interface UserFeign {
@PostMapping
void save(User user);
}
@Component
public class UserFeignFactory implements FallbackFactory
private final UserFeignFallback userFeignFallback;
public UserFeignFactory(UserFeignFallback userFeignFallback) {
this.userFeignFallback = userFeignFallback;
}
@Override
public UserFeign create(Throwable cause) {
//打印下异常
cause.printStackTrace();
return userFeignFallback;
}
这里用到了第一种里写的UserFeignFallback ,这里需要注意的create方法返回值类型一定要实现Feign接口,否则会报错。
这里也可以这么写(其实一样):
@Component
public class UserFeignFactory implements FallbackFactory
@Override
public UserFeign create(Throwable cause) {
//打印下异常
cause.printStackTrace();
return new UserFeign {
@Override
public void save(User user) {
}
};
}
ErrorDecoder接口处理请求错误信息,默认实现ErrorDecoder.Default抛出FeignException异常
FeignException.status 方法返回HTTP状态码,FallbackFactory.create默认情况下可以强制转换成FeignException异常这样就可以获取到HTTP状态码了。
错误解码实现类MyErrorDecoder
public class MyErrorDecoder implements ErrorDecoder {
@Override
public Exception decode(String methodKey, Response response) {
return new MyFeignException(methodKey,response);
}
}
自定义异常MyFeignException
public class MyFeignException extends RuntimeException {
private final String methodKey;
private Response response;
MyFeignException(String methodKey, Response response) {
this.methodKey = methodKey;
this.response = response;
}
public Response getResponse() {
return response;
}
public String getMethodKey() {
return methodKey;
}
}
第一种(application.properties):
全局配置,通过application.properties配置文件
feign.client.default-config=my-config feign.client.config.my-config.error-decoder=com.example.feign.MyErrorDecoder
( feign:
client:
default:
config: error-decoder:com.ruoyi.system.feign.factory.MyErrordecoder)实测这么写才对。
第二种:@EnableFeignClients
全局配置,@EnableFeignClients.defaultConfiguration注解
@EnableFeignClients(
defaultConfiguration = FeignClientsConfig.class
)
@SpringBootApplication
public class FeignApplication {
public static void main(String[] args) {
SpringApplication.run(FeignApplication.class, args);
}
}
第三种:@FeignClient
作用范围是Feign接口,优先级要高于上面两种,@FeignClient.configuration 注解
@FeignClient(name = "user", decode404 = true,
fallbackFactory = UserFeignFactory.class,
configuration = FeignClientsConfig.class
)
public interface UserFeign {
@PostMapping
void save(User user);
}
一、FeignClient注解
FeignClient注解被@Target(ElementType.TYPE)修饰,表示FeignClient注解的作用目标在接口上
1 2 3 4 5 |
@FeignClient(name = "github-client", url = "https://api.github.com", configuration = GitHubExampleConfig.class) public interface GitHubClient { @RequestMapping(value = "/search/repositories", method = RequestMethod.GET) String searchRepo(@RequestParam("q") String queryStr); } |
声明接口之后,在代码中通过@Resource注入之后即可使用。@FeignClient标签的常用属性如下:
二、Feign Client 和@RequestMapping
当前工程中有和Feign Client中一样的Endpoint时,Feign Client的类上不能用@RequestMapping注解否则,当前工程该endpoint http请求且使用accpet时会报404
三、Feign请求超时问题
Hystrix默认的超时时间是1秒,如果超过这个时间尚未响应,将会进入fallback代码。而首次请求往往会比较慢(因为Spring的懒加载机制,要实例化一些类),这个响应时间可能就大于1秒了
解决方案有三种,以feign为例。
方法一
hystrix.command.default.execution.isolation.thread.timeoutInMilliseconds: 5000
该配置是让Hystrix的超时时间改为5秒
方法二
hystrix.command.default.execution.timeout.enabled: false
该配置,用于禁用Hystrix的超时时间
方法三
feign.hystrix.enabled: false
该配置,用于索性禁用feign的hystrix。该做法除非一些特殊场景,不推荐使用。