在一个分布式系统里,许多依赖不可避免的会调用失败,比如超时、异常等,如何能够保证在一个依赖出问题的情况下,不会导致整体服务失败,这个就是Hystrix需要做的事情。Hystrix提供了熔断、隔离、Fallback、cache、监控等功能,能够在一个、或多个依赖同时出现问题时保证系统依然可用。知道它的,作用优点和好处了。那么下边就跟着我一起来操作一下feign整合Hystrix。
1.pom文件
4.0.0
feign-customizing
jar
com.itmuch.cloud
microservice-spring-cloud
0.0.1-SNAPSHOT
UTF-8
UTF-8
1.8
org.springframework.boot
spring-boot-starter-web
org.springframework.cloud
spring-cloud-starter-eureka
org.springframework.boot
spring-boot-starter-actuator
org.springframework.cloud
spring-cloud-starter-feign
org.springframework.cloud
spring-cloud-starter-hystrix-dashboard
org.springframework.cloud
spring-cloud-starter-hystrix
---------------pom文件的注意点就是一定要注意springboot的版本,版本不能太高。否则会报错找不到方法的异常。具体分析在后续博客中会详细分析。
2.配置文件:
application.yml文件
spring:
application:
name: microservice-consumer-movie
server:
port: 2000
eureka:
client:
healthcheck:
enabled: true
serviceUrl:
defaultZone: http://47.xxx.6.xxx:1000/eureka
instance:
prefer-ip-address: true
logging:
level:
com.itmuch.cloud.feign.UserFeignClient: DEBUG
注意点:
#可以通过下边的配置设置超时时间,默认为一秒即为1000:
也可以通过下边的设置来更好的观察项目的效果
# hystrix.command.default.execution.isolation.thread.timeoutInMilliseconds: 5000
# 或者:
# hystrix.command.default.execution.timeout.enabled: false
# 或者:
feign.hystrix.enabled: true ## 索性禁用feign的hystrix
# 超时的issue:https://github.com/spring-cloud/spring-cloud-netflix/issues/768
# 超时的解决方案: http://stackoverflow.com/questions/27375557/hystrix-command-fails-with-timed-out-and-no-fallback-available
# hystrix配置: https://github.com/Netflix/Hystrix/wiki/Configuration#execution.isolation.thread.timeoutInMilliseconds
3,启动类
Applicatoin
import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;
import org.springframework.cloud.client.discovery.EnableDiscoveryClient;
import org.springframework.cloud.netflix.eureka.EnableEurekaClient;
import org.springframework.cloud.netflix.feign.EnableFeignClients;
import org.springframework.cloud.netflix.hystrix.dashboard.EnableHystrixDashboard;
@SpringBootApplication
@EnableDiscoveryClient
@EnableFeignClients
@EnableHystrixDashboard
public class MyFeignApplication {
public static void main(String[] args) {
SpringApplication.run(MyFeignApplication.class, args);
}
}
注意点:四个注解缺一不可:
@SpringBootApplication
@EnableDiscoveryClient
@EnableFeignClients
@EnableHystrixDashboard
4.建立controller
package com.itmuch.cloud.controller;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.PathVariable;
import org.springframework.web.bind.annotation.RequestMapping;
import com.itmuch.cloud.entity.User;
import com.itmuch.cloud.feign.FeignClient2;
import com.itmuch.cloud.feign.UserFeignClient;
@RestController
public class TestController {
@Autowired
private UserFeignClient userFeignClient;
@RequestMapping("/index")
public String index() {
String str = userFeignClient.getContext();
return str;
}
}
这里的controller是一个外部入口,通过请求index方法进而调用下边的feign方法,
5.feign的接口配置(重点)
import org.springframework.cloud.netflix.feign.FeignClient;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RequestMethod;
@FeignClient(name = "feign-user", fallback = MyHystrix.class)
public interface UserFeignClient {
@RequestMapping(value="/getContext",method=RequestMethod.GET)
public String getContext();
}
注意点:@FeignClient(name = "feign-user", fallback = MyHystrix.class) 这里就是feign的核心配置,name属性是feign请求外部接口的服务名称(就是一同注册到注册中心的服务名称) fallback就是产生异常错误后的回退路径
要求fallback指向的类必须实现feign接口。然后再对应的接口的实现具体实现自定义 的异常处理(抛错,提示异常,回退等操作)。注意点2feign中 的方法注解不支持GetMapping 以及如果是@PathVariable一定要有值。
附加fallback的类
import org.springframework.stereotype.Component;
@Component
public class MyHystrix implements UserFeignClient {
@Override
public String getContext() {
System.err.println("=======报错");
return "报错了";
}
}
说明,如果是UserFeignClient的某个方法由于超时,异常等非正常操作都会进入对应Hystrix方法中,这样更好地捕获异常和进行处理。
6.新建一个项目作为feign的请求项目,要求该项目也能够注册到注册中心上(eureka等)
下边不做详细说明核心代码如下:
7.pom文件
4.0.0
movie-feign
jar
com.itmuch.cloud
microservice-spring-cloud
0.0.1-SNAPSHOT
UTF-8
UTF-8
1.8
org.springframework.boot
spring-boot-starter-web
org.springframework.cloud
spring-cloud-starter-eureka
org.springframework.boot
spring-boot-starter-actuator
org.springframework.cloud
spring-cloud-starter-feign
8.application.yml
spring:
application:
name: provider-user
server:
port: 2001
eureka:
client:
healthcheck:
enabled: true
serviceUrl:
defaultZone: http://47.xxx.6.xxx:1000/eureka
instance:
prefer-ip-address: true
9.请求端controller
package com.itmuch.cloud.controller;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.PathVariable;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;
import com.itmuch.cloud.entity.User;
import com.itmuch.cloud.feign.UserFeignClient;
@RestController
public class MovieController {
/*
* @GetMapping("/test") public User testPost(User user) { return
* this.userFeignClient.postUser(); }
*
* @GetMapping("/test-get") public User testGet(User user) { return
* this.userFeignClient.getUser(user); }
*/
@RequestMapping("/getContext")
public String getContext() {
return "我是服务端的getContext方法";
}
}
10.最后来波效果图:
10-1eureka注册中心
1
10-2 失败结果
10-3成功