SpringCloud 微服務 (十五) 服務容錯 Hystrix

工做中的微服務架構,某個服務一般會被多個服務調用或者多層調用完成需求,若是某個服務不可用,致使一個系統功能不可用或者服務直接沒用了的狀況,這種狀況稱爲雪崩效應html

有A服務調用B服務,B服務調用C服務,若是B服務調用C服務出了問題,那麼B服務會一直重試,等待會將資源耗盡,結果B服務也不可用,致使A服務調用B服務的時候,也出問題,這樣的話,ABC服務都癱了java

爲預防以上問題,在下面學習Spring Cloud Hystrix,防雪崩,容錯機制,基於NetFlix的Hystrixspring

Hystrix翻譯中文是豪豬的意思,沒見過也知道防護力很高的樣子,還有以前學習的Eureka翻譯中文的意思是找到了,就是後來詞化成發現docker

Hystrix 供分佈式系統使用,提供延遲和容錯功能,隔離遠程系統、訪問和第三方程序庫的訪問設計模式

 

Spring Cloud Hystrix服務器

①服務降級網絡

②服務熔斷架構

③依賴隔離app

④監控(Hystrix Dashboard)maven

根據以上特性功能開始學習

 

服務降級

這個功能其實咱們平時也都見過,好比訪問某寶頁面搶購,某奇藝看東西會提示: 網絡開小差了,請稍後再試 等相似的提示

服務降級主導思想是區分業務,詳細體如今優先核心服務,非核心服務不可用或放低其可用度,就有一種棄車保帥的意思,舍小保大

假設一個電商系統,某天的交易有巨大的流量出現,擺好的服務器資源就這麼多,那麼優先保證商品、訂單、支付等服務的可用性,另外好比廣告、積分等就屬於非核心服務,那麼就能夠調度一下

細分到服務,好比商品服務,購買的時候,買家查詢頻繁度遠高於賣家查詢,那麼就能夠調度買家查詢爲核心服務,優先保證其可用性,另外買家查詢服務就屬於非核心服務,實際還須要根據業務場景調度

Hystrix的使用,經過@HystrixCommand註解,fallbackMethod回退函數實現降級邏輯

在以前的order服務和product服務進行學習,主要學習組件內容,按套路出牌

order服務

第一步maven加入Hystrix的依賴

<dependency>
    <groupId>org.springframework.cloud</groupId>
    <artifactId>spring-cloud-starter-hystrix</artifactId>
</dependency>

注意: 若是後面@DefaultProperties註解沒法導入的話,在依賴上把版本號<version>加上

凡是遇到這樣的問題,大多數緣由是官方把這個包名改過了,爲了繼續使用原來已經使用過的組件依賴,要求加上version指定版本,才能夠

這邊spring-cloud-starter-hystrix的名字在spring cloud 2.0.3發佈的正式版中改爲了spring-cloud-starter-netflix-hystrix

因此引入依賴,改爲如下寫法就能夠了

<dependency>
    <groupId>org.springframework.cloud</groupId>
    <artifactId>spring-cloud-starter-netflix-hystrix</artifactId>
</dependency>

 

第二步在啓動類上,將以前的註解替換成@SpringCloudApplication,

該註解包含@SpringBootApplication @EnableDiscoveryClient @EnableCircuitBreaker三個註解的效果

從這點你們就能夠明白怎麼整合註解功能的使用

@SpringCloudApplication
@EnableFeignClients
public class OrderApplication {
    public static void main(String[] args) {
        SpringApplication.run(OrderApplication.class, args);
    }
}

 

第三步建立一個controller測試代碼

/**
 * 測試 使用hystrix
 */
@RestController
@DefaultProperties(defaultFallback = "defaultFallback")
public class HystrixController {
    /**
     * HystrixCommandProperties 參數對應查看
     * 下面超時配置
     */
    @HystrixCommand(
            commandProperties = {
                    @HystrixProperty(name = "execution.isolation.thread.timeoutInMilliseconds",
                                     value = "3000")
            }
    )
    @GetMapping("/list")
    public String list() {
        RestTemplate restTemplate=new RestTemplate();
        String s=restTemplate.postForObject("http://192.168.5.102:9001/product/list",
        Arrays.asList("1"),String.class);
        return s;
    }

    public String defaultFallback() {
        return "拼命加載中...";
    }
}

簡單的測試降級,請求發送會觸發defaultFallback的返回,相關配置信息也不用記,實在太長了,知道在哪裏就能夠了,若是不出現降級,能夠去url請求的終端服務作點小手腳,好比thread.sleep(xxx)

 

依賴隔離

依賴隔離就想到以前學習的docker,也具備隔離特性,docker實現進程的隔離,使容器以前互不影響,回來Hystrix,他使用的是線程池隔離方式,Hystrix會爲每個hystrixcommand建立獨立的線程池,你就像上面測試的某一個依賴服務,並不會拖慢影響其餘的服務,Hystrix自動實現依賴隔離

 

熔斷機制

微服務分佈式容錯機制必需要考慮,到目前知道的方式主要兩種,

①重試機制: 對應預期短暫的故障問題

②斷路器模式: 對應更長時間的故障問題,該模式是將受保護的服務封裝在一個能夠監控故障的斷路器對象中,當該服務的故障達到閥值,斷路器就會採起措施,跳閘斷路,斷路器對象被採起返回錯誤的方式告之

martin fowler發的一篇文章,關於CircuitBreaker(斷路器),

URL: https://martinfowler.com/bliki/CircuitBreaker.html

拿其中的執行狀態機制圖,作一個翻譯學習

以上解釋到斷路器設計模式---狀態機制,能夠看出有三種狀態closed、open、half open, 顧名思義,以熔斷路爲主角

closed: 熔斷器關閉狀態,調用失敗次數累計達到閥值,就會啓動熔斷機制

open/half open: 熔斷器打開狀態,此時對服務都直接返回錯誤,該處設計時鐘概念,到了點就會進入half open狀態,運行一些服務請求,若是請求是成功的,就認爲服務恢復了,關閉熔斷器closed,不然就繼續fail回到open狀態

 

代碼中註解配置寫法相似超時設置,主要參數以及說明 以下:

/**
 * HystrixCommandProperties 參數對應查看
 * @return
 */
@HystrixCommand(
        commandProperties = {
                //超時設置
                @HystrixProperty(name = "execution.isolation.thread.timeoutInMilliseconds",
                                 value = "2000"),
                //設置熔斷
                @HystrixProperty(name = "circuitBreaker.enabled",value = "true"),
                //設置滾動窗口中,斷路器的最小請求數量
                @HystrixProperty(name = "circuitBreaker.requestVolumeThreshold",value = "10"),
                //斷路器肯定是否須要打開統計請求和錯誤數據的時候,具備一個時間範圍即時間窗口,當斷路器打開,
                //對主邏輯進行熔斷以後,hystrix會啓動休眠時間窗,此時降級邏輯會稱爲主邏輯,當休眠時間窗到期,斷路           
                //器就進入half open狀態
                //嘗試釋放請求到原主邏輯上,就想以前描述的,成功則斷路器閉合closed,失敗則繼續打開open,休眠時間
                //窗將從新計時
                //如下設置休眠時間窗爲10000毫秒
                @HystrixProperty(name = "circuitBreaker.sleepWindowInMilliseconds",
                                 value = "10000"),
                //設置斷路器打開的百分比條件,
                //好比此處設置爲60,在滾動窗口中發生了10次request,有7次發生了異常,超出設置值,則斷路器就進入
                //open狀態,反之即closed
                @HystrixProperty(name = "circuitBreaker.errorThresholdPercentage",value = "60")
        }
)
@GetMapping("/list")
public String list() {
   ......
}

 

以上是粗略學習hystrix,因此配置都寫在了註解上面,下面轉化配置文件,以超時設置爲例,上面服務中的方法名字是list,下面設置一個默認超時設置和一個針對list方法的超時設置,在方法上須要加上@HystrixCommand註釋,該註解有一個commandKey參數,指定該方法的key使用斷路器,若是不設置默認是方法的名字,此處沒有其餘方法,圖方便就直接用名字

hystrix:
  command:
    default:
      execution:
        isolation:
          thread:
            timeoutInMilliseconds: 2500
    list:
      execution:
        isolation:
          thread:
            timeoutInMilliseconds: 2800

 

關於Hystrix還有控制面板能夠觀察調控的更清晰,還有結合Hystrix+feign等方面的使用,繼續學習

-------------------------------------------------------------

相關文章
相關標籤/搜索