微服務架構中,根據業務將架構拆成一個個服務,服務與服務之間可以相互調用(RPC),SpringCloud中可以通過RestTemplate+Ribbon和Feign調用。爲了保證高可用,單個服務通常會集羣部署,由於網絡等種種原因,服務不可能100%可用,如果單個服務出現問題,調用這個服務就會出現線程阻塞,此時若出現大量請求涌入,Servlet容器的線程資源會很快被消耗完畢,導致服務癱瘓。
服務與服務之間的依賴性,導致故障會傳播,會對整個微服務系統造成災難性的嚴重後果。這就是服務故障的雪崩效應。
爲了解決這個問題,業界提出了斷路器模型。
一、介紹
Netflix has created a library called Hystrix that implements the circuit breaker pattern. In a microservice architecture it is common to have multiple layers of service calls.
Netflix開源了Hystrix組件,實現了斷路器模式。SpringCloud對其進行了整合。
在微服務架構中,一個請求調用多個服務是非常常見的。
較底層的服務如果出現故障,會導致連鎖故障。當對特定的服務調用不可用達到一定的閥值(Hystrix默認是5秒20次),就會打開斷路器。
斷路打開後,可用避免連鎖故障,Fallback可以直接返回一個固定值。
二、在Ribbon使用斷路器
在ribbon項目中引入Hystrix.
1. 需要引入Hystrix的依賴
<dependency>
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-starter-netflix-hystrix</artifactId>
</dependency>
注意如果是F版本的SpringCloud,這裏要引 spring-cloud-starter-netflix-hystrix而不是spring-cloud-starter-hystrix,否則啓動會報錯。2.在啓動類上開啓@EnableHystrix註解
@SpringCloudApplication
@EnableDiscoveryClient
@EnableHystrix
public class RibbonApplication {
public static void main(String[] args) {
SpringApplication.run(RibbonApplication.class, args);
}
@Bean
@LoadBalanced
RestTemplate getRestTemplate(){
return new RestTemplate();
}
}
3. 在需要創建斷路器的service方法上開啓@HystrixCommand註解,並制定fallbackMethod方法
@Service
public class SayService {
@Autowired
RestTemplate restTemplate;
@HystrixCommand(fallbackMethod = "error")
public String saySomeWord(String name) {
return restTemplate.getForObject("http://SERVICE-HI/say?name="+name, String.class);
}
public String error(String name) {
return "[Error] sorry," + name;
}
}
這裏我們不開啓服務,然後通過Ribbon去調用服務 http://localhost:8764/say?name=long_tian
開啓service-hi服務,過大概5秒再次訪問
三、在Feign使用Hystrix
方法一:引入spring-cloud-starter-netflix-hystrix依賴,然後跟Ribbon中一樣在Controller中的方法上開啓@HystrixCommand註解,創建fallbackMethod。
方法二:Feign自帶Hystrix。但是默認是關閉的,需要修改配置打開。
feign:
hystrix:
enabled: true
引入依賴,在FeignClient接口的@FeignClient註解上加上fallbanck指定類。該類要實現FeignClient接口。
@FeignClient(value = "service-hi", fallback = SchedualServiceHystric.class)
public interface SchedualServiceHi {
@RequestMapping(value="/say",method = RequestMethod.GET)
String sayHiFromClientOne(@RequestParam(value = "name") String name);
}
代碼中的SchedualServiceHystric,實現了FeignClient,所以它變成了FeignClient的fallback類。將它注入到IoC容器。
@Component
public class SchedualServiceHystric implements SchedualServiceHi {
@Override
public String sayHiFromClientOne(String name) {
return "sorry,Mr."+name+",service failed.";
}
}
啓動feign工程,service工程,訪問http://localhost:8765/hello?name=long_tian 再關閉service工程,再次訪問
說明斷路器生效了。
四、Hystrix儀表盤
Hystrix Dashborad用於實時監控Hystrix的各項指標信息。
1.引入依賴
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-actuator</artifactId>
</dependency>
<dependency>
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-starter-hystrix-dashboard</artifactId>
</dependency>
2.在程序啓動類上開啓註解@EnableHystrixDashboard@SpringBootApplication
@EnableEurekaClient
@EnableFeignClients
@EnableHystrix
@EnableHystrixDashboard
public class FeignApplication {
public static void main(String[] args) {
SpringApplication.run(FeignApplication.class, args);
}
}
3. 訪問 http://localhost:8765/hystrix,界面如下
HystrixDashboard支持三種監控方式:
默認的集羣監控:通過URL http://turbine-hostname:port/turbine.stream 開啓,實現對默認集羣的監控。
制定的集羣監控: 通過URL http://turbine-hostname:port/turbine.stream?cluster=[clusterName] 開啓,實現對集羣clusterName的監控。
單體應用的監控:通過URL http://hystrix-app:port/hystrix.stream 開啓,實現對某個實例的監控。
* Delay:控制服務器上輪詢監控信息的延遲時間,默認爲2000毫秒,可以通過配置該屬性來降低客戶端的網絡和CPU的消耗。
* Title:用於展示的標題。
這裏我們通過http://localhost:8765/hystrix.stream 監控之前創建的Hystrix。
訪問一次 http://localhost:8765/hello?name=long_tian 調用一次服務,可以看到調用成功一次。
關掉被調用的服務,訪問,可以看到調用失敗。
在監控界面有兩個重要的圖形信息:一個實心圓和一條曲線。
* 實心圓:
1. 顏色。顏色的變化代表了實例的健康程度,健康程度從綠色、黃色、橙色、紅色遞減。
2. 大小。表示請求流量發生變化,流量越大實心圓越大。
所以可以通過實心圓發現大量實例中的故障實例和高壓實例。
* 折線:
用來記錄2分鐘內流量的相對變化情況。可以通過它可以觀察留下的上升下降趨勢。