Hystrix斷路器簡介及應用

Hystrix斷路器簡介
 
Hystrix對應的中文名字是“豪豬”,豪豬身上長滿了刺,能保護自己不受天敵的傷害,代表了一種防禦機制,這與Hystrix本身的功能不謀而合,因此Netflix團隊將該框架命名爲Hystrix,並使用了對應的卡通形象做作爲Logo:

在一個分佈式系統裏,許多依賴不可避免的會調用失敗,比如超時、異常等,如何能夠保證在一個依賴出問題的情況下,不會導致整體服務失敗,這個就是Hystrix需要做的事情。Hystrix提供了熔斷、隔離、Fallback、cache、監控等功能,能夠在一個或多個依賴同時出現問題時保證系統依然可用
 

服務雪崩效應

當一個請求依賴多個服務的時候,正常情況下的訪問如下圖所示:

但是當請求的服務中出現無法訪問、異常、超時等問題時(圖中的I),那麼用戶的請求將會被阻塞:

如果多個用戶的請求中都存在無法訪問的服務,那麼他們都將陷入阻塞的狀態中:

Hystrix的引入,可以通過服務熔斷和服務降級來解決這個問題

Hystrix服務熔斷與服務降級

熔斷機制是應對雪崩效應的一種微服務鏈路保護機制。即當某個服務不可用或者響應時間超時時,會進行服務降級,進而熔斷該節點的服務調用,並快速返回自定義的錯誤以及頁面信息

寫個項目來測試下:參考microservice-student-provider-hystrix-1001模塊新建一個帶服務熔斷的服務提供者模塊(microservice-student-provider-hystrix-1004),把配置和代碼都複製一份到這個項目裏,然後進行修改

1、在pom.xml里加入Hystrix的依賴:

<!--Hystrix相關依賴-->
<dependency>
	<groupId>org.springframework.cloud</groupId>
	<artifactId>spring-cloud-starter-hystrix</artifactId>
</dependency>

2、在application.yml裏修改下端口和實例名稱:

server:
  port: 1004
  context-path: /
spring:
  application:
    name: microservice-student
  datasource:
    type: com.alibaba.druid.pool.DruidDataSource
    driver-class-name: com.mysql.jdbc.Driver
    url: jdbc:mysql://localhost:3306/demosite1?useUnicode=true&characterEncoding=utf8
    username: root
    password: root
  jpa:
    hibernate:
      ddl-auto: update
    show-sql: true

eureka:
  instance:
    #eureka客戶端主機實例名稱
    hostname: localhost
    #客戶端服務名
    appname: microservice-student
    #客戶端實例名稱
    instance-id: microservice-student:1004
    #顯示IP
    prefer-ip-address: true
  client:
    service-url:
      #把服務註冊到eureka註冊中心
      defaultZone: http://eureka2001.test.com:2001/eureka/,http://eureka2002.test.com:2002/eureka/,http://eureka2003.test.com:2003/eureka/
info:
  groupId: com.ue.microservice
  artifactId: microservice-student-provider-1004
  version: 1.0-SNAPSHOT
  負責人: Tom
  聯繫電話: 123456

3、在啓動類MicroserviceStudentProviderHystrix1004Application.java加入@EnableCircuitBreaker註解:

4、在服務提供者1004項目中的controller新增測試接口:

@Value("${server.port}")
private String port;

/**
 * 測試Hystrix服務降級
 * @return
 * @throws InterruptedException
 */
@GetMapping(value="/hystrix")
@HystrixCommand(fallbackMethod="hystrixFallback")
public Map<String,Object> hystrix() throws InterruptedException{
	Thread.sleep(4000);
	Map<String,Object> map=new HashMap<String,Object>();
	map.put("code", 200);
	map.put("info","工號【" + port + "】正在爲您服務");
	return map;
}

public Map<String,Object> hystrixFallback() throws InterruptedException{
	Map<String,Object> map=new HashMap<String,Object>();
	map.put("code", 500);
	map.put("info", "系統【" + port + "】繁忙,稍後重試");
	return map;
}

上述接口如果能正常訪問,那返回的是200跟業務數據,但是這裏用了Thread.sleep(2000)來模擬超時,在接口上面加上@HystrixCommand註解以及fallbackMethod,表明這個方法在沒有異常以及沒有超時(hystrix默認1秒算超時)的情況下,才返回正常的業務數據;否則,會進入fallback指定的本地方法,這裏搞的是返回500跟系統繁忙,稍後重試,可以有效的解決雪崩效應以及返回給用戶界面很好的報錯提示信息

5、在服務消費者80項目中的controller新增測試接口:

/**
 * 測試Hystrix服務降級
 * @return
 */
@GetMapping(value="/hystrix")
@ResponseBody
public Map<String,Object> hystrix(){
	return restTemplate.getForObject(PRE_HOST + "/student/hystrix", Map.class);
}

6、開始測試,先啓動三個eureka,再啓動帶hystrix的provider,最後啓動普通的consumer:

然後在瀏覽器地址欄輸入http://localhost/student/hystrix,結果如下:

因爲Hystrix默認1秒就算超時,但線程sleep了2秒,所以會進入到自定義的fallback方法,防止服務雪崩

這裏再將sleep修改成100毫秒進行測試,結果如下:

可以看到返回了正常的業務數據

Hystrix默認超時時間設置

Hystrix默認超時時間是1秒,可以通過Hystrix源碼找到,找到hystrix-core.jar的com.netflix.hystrix包下的HystrixCommandProperties類,類裏有一個default_executionTimeoutInMilliseconds屬性,這個就是默認的超時時間:

系統裏假如要自定義設置Hystrix的默認時間的話,可在application.yml配置文件里加上:

#將Hystrix的默認超時時間設置爲3秒
hystrix:
  command:
    default:
      execution:
        isolation:
          thread:
            timeoutInMilliseconds: 3000

然後在代碼裏將sleep修改成2秒進行測試,結果如下:

再將sleep修改成4秒進行測試,結果如下:

 
以上就是本篇博客的全部內容,Hystrix斷路器主要應用於解決雪崩效應
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章