Hystrix是什麼?
Hystrix 能使你的系統在出現依賴服務失效的時候,通過隔離系統所依賴的服務,防止服務級聯失敗,同時提供失敗回退機制,更優雅地應對失效,並使你的系統能更快地從異常中恢復。
Hystrix能做什麼?
在通過第三方客戶端訪問(通常是通過網絡)依賴服務出現高延遲或者失敗時,爲系統提供保護和控制
在分佈式系統中防止級聯失敗
快速失敗(Fail fast)同時能快速恢復
提供失敗回退(Fallback)和優雅的服務降級機制
提供近實時的監控、報警和運維控制手段
Hystrix設計原則?
防止單個依賴耗盡容器(例如 Tomcat)內所有用戶線程
降低系統負載,對無法及時處理的請求快速失敗(fail fast)而不是排隊
提供失敗回退,以在必要時讓失效對用戶透明化
使用隔離機制(例如『艙壁』/『泳道』模式,熔斷器模式等)降低依賴服務對整個系統的影響
針對系統服務的度量、監控和報警,提供優化以滿足近實時性的要求
在 Hystrix 絕大部分需要動態調整配置並快速部署到所有應用方面,提供優化以滿足快速恢復的要求
能保護應用不受依賴服務的整個執行過程中失敗的影響,而不僅僅是網絡請求
Hystrix實現原理-命令模式
將所有請求外部系統(或者叫依賴服務)的邏輯封裝到 HystrixCommand或者HystrixObservableCommand(依賴RxJava)對象中
Run()方法爲要實現的業務邏輯,這些邏輯將會在獨立的線程中被執行當請求依賴服務時出現拒絕服務、超時或者短路(多個依賴服務順序請求,前面的依賴服務請求失敗,則後面的請求不會發出)時,執行該依賴服務的失敗回退邏輯(Fallback)
Hystrix實現原理-艙壁模式
貨船爲了進行防止漏水和火災的擴散,會將貨倉分隔爲多個,當發生災害時,將所在貨倉進行隔離就可以降低整艘船的風險。
Hystrix實現原理-隔離策略
應用在複雜的分佈式結構中,可能會依賴許多其他的服務,並且這些服務都不可避免地有失效的可能。如果一個應用沒有與依賴服務的失效隔離開來,那麼它將有可能因爲依賴服務的失效而失效。
Hystrix將貨倉模式運用到了服務調用者上。爲每一個依賴服務維護一個線程池(或者信號量),當線程池佔滿,該依賴服務將會立即拒絕服務而不是排隊等待。
每個依賴服務都被隔離開來,Hystrix 會嚴格控制其對資源的佔用,並在任何失效發生時,執行失敗回退邏輯。
Hystrix實現原理-觀察者模式
Hystrix通過觀察者模式對服務進行狀態監聽。
每個任務都包含有一個對應的Metrics,所有Metrics都由一個ConcurrentHashMap來進行維護,Key是CommandKey.name()
在任務的不同階段會往Metrics中寫入不同的信息,Metrics會對統計到的歷史信息進行統計彙總,供熔斷器以及Dashboard監控時使用。
Metrics
Metrics內部又包含了許多內部用來管理各種狀態的類,所有的狀態都是由這些類管理的
各種狀態的內部也是用ConcurrentHashMap來進行維護的
如:HealthCountsStream是用來統計任務失敗率的一個類
而每個狀態管理類內部又包含了各自的真實轉態信息
如HealthCountsStream保存的信息的一部分如下:
Metrics如何統計
Metrics在統計各種狀態時,時運用滑動窗口思想進行統計的,在一個滑動窗口時間中又劃分了若干個Bucket(滑動窗口時間與Bucket成整數倍關係),滑動窗口的移動是以Bucket爲單位進行滑動的。
如:HealthCounts 記錄的是一個Buckets的監控狀態,Buckets爲一個滑動窗口的一小部分,如果一個滑動窗口時間爲 t ,Bucket數量爲 n,那麼每t/n秒將新建一個HealthCounts對象。
Hystrix實現原理-熔斷機制
熔斷是參考電路而產生的一種保護性機制,即系統中如果存在某個服務失敗率過高時,將開啓熔斷器,對於後續的調用,不在繼續請求服務,而是進行Fallback操作。
熔斷所依靠的數據即是Metrics中的HealthCount所統計的錯誤率。
一個命令的調用過程如圖所示:
熔斷器的判斷流程:
1.一個命令執行前會先運行allowRequest()函數。
allowRequest()函數內部爲:
先查看熔斷器是否強制開啓(ForceOpen()),如果開啓則拒絕
再查看熔斷器是否強制關閉(ForceClosed()),如果強制關閉則允許Request,否則進一步判斷
先做isOpen(),判斷熔斷器是否開啓,如果開啓則拒絕訪問,如果開啓則進一步判斷
再做allowSingleTest(),熔斷器休眠期過後,允許且只允許一個請求,如果這個請求正確執行,則熔斷器關閉,如果執行失敗,則熔斷器再次開啓,進入新的熔斷週期。
如何判斷超時
在運行對應的command時,Hystrix會註冊一個Timer到一個定時線程池中,當超時後會啓用一個HystrixTimer線程來終止的執行。
線程池的管理是用ThreadPoolExecutor來實現的,當線程池和阻塞隊列都滿後會拋出RejectedExecutionException,捕獲該異常並進行相應狀態的處理。
Note:除此之外由程序錯誤導致的異常,斷路器打開都可以導致任務失敗進入Fallback
失敗降級
Hystrix提供了失敗降級策略,當命令執行失敗時,Hystrix 將會執行失敗回退邏輯。失敗回退邏輯包含了通用的迴應信息,這些迴應從內存緩存中或者其他固定邏輯中得到,而不應有任何的網絡依賴。
如果一定要在失敗回退邏輯中包含網絡請求,必須將這些網絡請求包裝在另一個 HystrixCommand 或 HystrixObservableCommand 中。
失敗降級也有頻率限時,如果同一fallback短時間請求過大,則會拋出拒絕異常。
緩存機制
除了第一次請求需要真正訪問依賴服務以外,後續請求全部從緩存中獲取,可以保證在同一個用戶請求內,不會出現依賴服務返回不同的迴應的情況,且避免了不必要的線程執行。
緩存在命令內部,且有一個ConcurrentHashMap進行管理
使用緩存需要重寫父類的getCacheKey方法
配置
Command
設置隔離策略 execution.isolation.strategy = THREAD 設置超時時間 execution.isolation.thread.timeoutInMilliseconds = 1000 信號量隔離策略設置最大併發請求數(僅在信號量隔離策略下生效) execution.isolation.semaphore.maxConcurrentRequests = 10 設置最大Fallback數量 fallback.isolation.semaphore.maxConcurrentRequests = 10 設置熔斷器滑動窗口最小任務 circuitBreaker.requestVolumeThreshold = 20 設置熔斷器持續時間 circuitBreaker.sleepWindowInMilliseconds = 5000 設置觸發熔斷器的失敗任務閾值(百分比) circuitBreaker.errorThresholdPercentage = 50 設置Metrics監視器的範圍時間(過去多少ms內) metrics.rollingStats.timeInMilliseconds = 10000 設置監視器內桶的數量(將監視器範圍劃分爲若干塊) metrics.rollingStats.numBuckets= 10123456789101112131415161718192021222324252627
ThreadPool
設置線程池容量 coreSize = 10 設置阻塞隊列長度(優先級高於queueSizeRejectionThreshold,且一旦初始化就不能更改 ) maxQueueSize = -1 動態設置阻塞隊列長度 queueSizeRejectionThreshold = 5 空閒線程存活時間 keepAliveTimeMinutes= 1 線程池監控窗口時間範圍(10s內) metrics.rollingStats.timeInMilliseconds = 10000 設置線程池監控滑動窗口的桶數量 metrics.rollingStats.numBuckets = 500123456789101112131415161718
Note:窗口時間必須爲桶數量的整數倍,否則會拋出異常
Dashboard
1.Hystrix 自帶了一個dashboard,用來監控熔斷信息.
2.Dashboard可以監測哪些數據?
3.使用turbine可以監控集羣.
使用Turbine聚合的服務器集羣
遇到問題
壓測過不了,提高阻塞隊列和線程池無效,增加fallback容量解決。
fallback.isolation.semaphore.maxConcurrentRequests = 100
Hystrix配置簡單說明
Hystrix屬性的4中優先級
1. 內置全局默認值(Global default from code)
如果下面3種都沒有設置,默認是使用此種,後面用“默認值”代指這種。
2. 動態全局默認屬性(Dynamic global default property)
可以通過屬性配置來更改全局默認值,後面用“默認屬性”代指這種。
3. 內置實例默認值(Instance default from code)
在代碼中,設置的屬性值,後面用“實例默認”來代指這種。
4. 動態配置實例屬性(Dynamic instance property)
可以針對特定的實例,動態配置屬性值,來代替前面三種,後面用“實例屬性”來代指這種。
優先級:1 < 2 < 3 < 4
命令屬性
執行
execution.isolation.strategy
設置HystrixCommand.run()的隔離策略,有兩種選項:
THREAD —— 在固定大小線程池中,以單獨線程執行,併發請求數受限於線程池大小。
SEMAPHORE —— 在調用線程中執行,通過信號量來限制併發量。
默認值:THREAD(ExecutionIsolationStrategy.THREAD)
可選值:THREAD,SEMAPHORE
默認屬性:hystrix.command.default.execution.isolation.strategy
實例屬性:
hystrix.command.HystrixCommandKey.execution.isolation.strategy
實例默認的設置:
// to use thread isolation
HystrixCommandProperties.Setter()
.withExecutionIsolationStrategy(ExecutionIsolationStrategy.THREAD)
// to use semaphore isolation
HystrixCommandProperties.Setter()
.withExecutionIsolationStrategy(ExecutionIsolationStrategy.SEMAPHORE)
execution.isolation.thread.timeoutInMilliseconds
設置調用者等待命令執行的超時限制,超過此時間,HystrixCommand被標記爲TIMEOUT,並執行回退邏輯。
注意:超時會作用在HystrixCommand.queue(),即使調用者沒有調用get()去獲得Future對象。
默認值:1000(毫秒)
默認屬性:hystrix.command.default.execution.isolation.thread.timeoutInMilliseconds
實例屬性:hystrix.command.HystrixCommandKey.execution.isolation.thread.timeoutInMilliseconds
實例默認的設置:HystrixCommandProperties.Setter()
.withExecutionTimeoutInMilliseconds(int value)
execution.timeout.enabled
設置HystrixCommand.run()的執行是否有超時限制。
默認值:true
默認屬性:hystrix.command.default.execution.timeout.enabled
實例屬性:hystrix.command.HystrixCommandKey.execution.timeout.enabled
實例默認的設置:
HystrixCommandProperties.Setter()
.withExecutionTimeoutEnabled(boolean value)
execution.isolation.thread.interruptOnTimeout
設置HystrixCommand.run()的執行是否在超時發生時被中斷。
默認值:true
默認屬性:hystrix.command.default.execution.isolation.thread.interruptOnTimeout
實例屬性:hystrix.command.HystrixCommandKey.execution.isolation.thread.interruptOnTimeout
實例默認的設置:
HystrixCommandProperties.Setter()
.withExecutionIsolationThreadInterruptOnTimeout(boolean value)
execution.isolation.thread.interruptOnCancel
設置HystrixCommand.run()的執行但取消動作發生時候可以響應中斷。
默認值:false
默認屬性:hystrix.command.default.execution.isolation.thread.interruptOnCancel
實例屬性:hystrix.command.HystrixCommandKey.execution.isolation.thread.interruptOnCancel
實例默認的設置:
HystrixCommandProperties.Setter()
.withExecutionIsolationThreadInterruptOnCancel(boolean value)
execution.isolation.semaphore.maxConcurrentRequests
設置當使用ExecutionIsolationStrategy.SEMAPHORE時,HystrixCommand.run()方法允許的最大請求數。如果達到最大併發數時,後續請求會被拒絕。
信號量應該是容器(比如Tomcat)線程池一小部分,不能等於或者略小於容器線程池大小,否則起不到保護作用。
默認值:10
默認屬性:hystrix.command.default.execution.isolation.semaphore.maxConcurrentRequests
實例屬性:hystrix.command.HystrixCommandKey.execution.isolation.semaphore.maxConcurrentRequests
實例默認的設置:
HystrixCommandProperties.Setter()
.withExecutionIsolationSemaphoreMaxConcurrentRequests(int value)
回退
下面的屬性控制HystrixCommand.getFallback()執行。這些屬性對ExecutionIsolationStrategy.THREAD和ExecutionIsolationStrategy.SEMAPHORE都有效。
fallback.isolation.semaphore.maxConcurrentRequests
設置調用線程產生的HystrixCommand.getFallback()方法的允許最大請求數目。
如果達到最大併發數目,後續請求將會被拒絕,如果沒有實現回退,則拋出異常。
默認值:10
默認屬性:hystrix.command.default.fallback.isolation.semaphore.maxConcurrentRequests
實例屬性:hystrix.command.HystrixCommandKey.fallback.isolation.semaphore.maxConcurrentRequests
實例默認:
HystrixCommandProperties.Setter()
.withFallbackIsolationSemaphoreMaxConcurrentRequests(int value)
fallback.enabled
該屬性決定當故障或者拒絕發生時,一個調用將會去嘗試HystrixCommand.getFallback()。
默認值:true
默認屬性:hystrix.command.default.fallback.enabled
實例屬性:hystrix.command.HystrixCommandKey.fallback.enabled
實例默認的設置:HystrixCommandProperties.Setter()
.withFallbackEnabled(boolean value)
斷路器(Circuit Breaker)
circuitBreaker.enabled
設置斷路器是否起作用。
默認值:true
默認屬性:hystrix.command.default.circuitBreaker.enabled
實例屬性:hystrix.command.HystrixCommandKey.circuitBreaker.enabled
實例默認的設置:HystrixCommandProperties.Setter()
.withCircuitBreakerEnabled(boolean value)
circuitBreaker.requestVolumeThreshold
設置在一個滾動窗口中,打開斷路器的最少請求數。
比如:如果值是20,在一個窗口內(比如10秒),收到19個請求,即使這19個請求都失敗了,斷路器也不會打開。
默認值:20
默認屬性:hystrix.command.default.circuitBreaker.requestVolumeThreshold
實例屬性:hystrix.command.HystrixCommandKey.circuitBreaker.requestVolumeThreshold
實例默認的設置:HystrixCommandProperties.Setter()
.withCircuitBreakerRequestVolumeThreshold(int value)
circuitBreaker.sleepWindowInMilliseconds
設置在迴路被打開,拒絕請求到再次嘗試請求並決定迴路是否繼續打開的時間。
默認值:5000(毫秒)
默認屬性:hystrix.command.default.circuitBreaker.sleepWindowInMilliseconds
實例屬性:hystrix.command.HystrixCommandKey.circuitBreaker.sleepWindowInMilliseconds
實例默認的設置:
HystrixCommandProperties.Setter()
.withCircuitBreakerSleepWindowInMilliseconds(int value)
circuitBreaker.errorThresholdPercentage
設置打開回路並啓動回退邏輯的錯誤比率。
默認值:50
默認屬性:hystrix.command.default.circuitBreaker.errorThresholdPercentage
實例屬性:hystrix.command.HystrixCommandKey.circuitBreaker.errorThresholdPercentage
實例默認的設置:HystrixCommandProperties.Setter()
.withCircuitBreakerErrorThresholdPercentage(int value)
circuitBreaker.forceOpen
如果該屬性設置爲true,強制斷路器進入打開狀態,將會拒絕所有的請求。
該屬性優先級比circuitBreaker.forceClosed高。
默認值:false
默認屬性:hystrix.command.default.circuitBreaker.forceOpen
實例屬性:hystrix.command.HystrixCommandKey.circuitBreaker.forceOpen
實例默認的設置:HystrixCommandProperties.Setter()
.withCircuitBreakerForceOpen(boolean value)
circuitBreaker.forceClosed
如果該屬性設置爲true,強制斷路器進入關閉狀態,將會允許所有的請求,無視錯誤率。
默認值:false
默認屬性:hystrix.command.default.circuitBreaker.forceClosed
實例屬性:hystrix.command.HystrixCommandKey.circuitBreaker.forceClosed
實例默認的設置:HystrixCommandProperties.Setter()
.withCircuitBreakerForceClosed(boolean value)
請求上下文
requestCache.enabled
設置HystrixCommand.getCacheKey()是否啓用,由HystrixRequestCache通過請求緩存提供去重複數據功能。
默認值:true
默認屬性:hystrix.command.default.requestCache.enabled
實例屬性:hystrix.command.HystrixCommandKey.requestCache.enabled
實例默認的設置:HystrixCommandProperties.Setter()
.withRequestCacheEnabled(boolean value)
requestLog.enabled
設置HystrixCommand執行和事件是否要記錄日誌到HystrixRequestLog。
默認值:true
默認屬性:hystrix.command.default.requestLog.enabled
實例屬性:hystrix.command.HystrixCommandKey.requestLog.enabled
實例默認的設置:HystrixCommandProperties.Setter()
.withRequestLogEnabled(boolean value)
壓縮器屬性
下面的屬性可以控制HystrixCollapser行爲。
maxRequestsInBatch
設置觸發批處理執行之前,在批處理中允許的最大請求數。
默認值:Integer.MAX_VALUE
默認屬性:hystrix.collapser.default.maxRequestsInBatch
實例屬性:hystrix.collapser.HystrixCollapserKey.maxRequestsInBatch
實例默認的設置:HystrixCollapserProperties.Setter()
.withMaxRequestsInBatch(int value)
timerDelayInMilliseconds
設置批處理創建到執行之間的毫秒數。
默認值:10
默認屬性:hystrix.collapser.default.timerDelayInMilliseconds
實例屬性:hystrix.collapser.HystrixCollapserKey.timerDelayInMilliseconds
實例默認的設置:HystrixCollapserProperties.Setter()
.withTimerDelayInMilliseconds(int value)
requestCache.enabled
設置請求緩存是否對HystrixCollapser.execute()和HystrixCollapser.queue()的調用起作用。
默認值:true
默認屬性:hystrix.collapser.default.requestCache.enabled
實例屬性:hystrix.collapser.HystrixCollapserKey.requestCache.enabled
實例默認的設置:HystrixCollapserProperties.Setter()
.withRequestCacheEnabled(boolean value)
線程池屬性
coreSize
設置核心線程池大小。
默認值:10
默認屬性:hystrix.threadpool.default.coreSize
實例屬性:hystrix.threadpool.HystrixThreadPoolKey.coreSize
實例默認的設置:HystrixThreadPoolProperties.Setter()
.withCoreSize(int value)
maximumSize
1.5.9新增屬性,設置線程池最大值。這個是在不開始拒絕HystrixCommand的情況下支持的最大併發數。這個屬性起作用的前提是設置了allowMaximumSizeToDrivergeFromCoreSize。1.5.9之前,核心線程池大小和最大線程池大小總是相同的。
maxQueueSize
設置BlockingQueue最大的隊列值。
如果設置爲-1,那麼使用SynchronousQueue,否則正數將會使用LinkedBlockingQueue。
如果需要去除這些限制,允許隊列動態變化,可以參考queueSizeRejectionThreshold屬性。
修改SynchronousQueue和LinkedBlockingQueue需要重啓。
默認值:-1
默認屬性:hystrix.threadpool.default.maxQueueSize
實例屬性:hystrix.threadpool.HystrixThreadPoolKey.maxQueueSize
實例默認的設置:HystrixThreadPoolProperties.Setter()
.withMaxQueueSize(int value)
queueSizeRejectionThreshold
設置隊列拒絕的閾值——一個人爲設置的拒絕訪問的最大隊列值,即使maxQueueSize還沒有達到。
當將一個線程放入隊列等待執行時,HystrixCommand使用該屬性。
注意:如果maxQueueSize設置爲-1,該屬性不可用。
默認值:5
默認屬性:hystrix.threadpool.default.queueSizeRejectionThreshold
實例屬性:hystrix.threadpool.HystrixThreadPoolKey.queueSizeRejectionThreshold
實例默認的設置:HystrixThreadPoolProperties.Setter()
.withQueueSizeRejectionThreshold(int value)
keepAliveTimeMinutes
設置存活時間,單位分鐘。如果coreSize小於maximumSize,那麼該屬性控制一個線程從實用完成到被釋放的時間。
默認值:1
默認屬性:hystrix.threadpool.default.keepAliveTimeMinutes
實例屬性:hystrix.threadpool.HystrixThreadPoolKey.keepAliveTimeMinutes
實例默認的設置:HystrixThreadPoolProperties.Setter()
.withKeepAliveTimeMinutes(int value)
allowMaximumSizeToDivergeFromCoreSize
在1.5.9中新增的屬性。該屬性允許maximumSize起作用。屬性值可以等於或者大於coreSize值,設置coreSize小於maximumSize的線程池能夠支持maximumSize的併發數,但是會將不活躍的線程返回到系統中去。(詳見KeepAliveTimeMinutes)
默認值:false
默認屬性:hystrix.threadpool.default.allowMaximumSizeToDivergeFromCoreSize
實例屬性:hystrix.threadpool.HystrixThreadPoolKey.allowMaximumSizeToDivergeFromCoreSize
實例默認的設置:HystrixThreadPoolProperties.Setter()
.withAllowMaximumSizeToDivergeFromCoreSize(boolean value)
metrics.rollingStats.timeInMilliseconds
設置統計的滾動窗口的時間段大小。該屬性是線程池保持指標時間長短。
默認值:10000(毫秒)
默認屬性:hystrix.threadpool.default.metrics.rollingStats.timeInMilliseconds
實例屬性:hystrix.threadpool.HystrixThreadPoolKey.metrics.rollingStats.timeInMilliseconds
實例默認的設置:HystrixThreadPoolProperties.Setter()
.withMetricsRollingStatisticalWindowInMilliseconds(int value)
metrics.rollingStats.numBuckets
設置滾動的統計窗口被分成的桶(bucket)的數目。
注意:”metrics.rollingStats.timeInMilliseconds % metrics.rollingStats.numBuckets == 0"必須爲true,否則會拋出異常。
默認值:10
可能的值:任何能被metrics.rollingStats.timeInMilliseconds整除的值。
默認屬性:hystrix.threadpool.default.metrics.rollingStats.numBuckets
實例屬性:hystrix.threadpool.HystrixThreadPoolProperties.metrics.rollingStats.numBuckets
實例默認的設置:HystrixThreadPoolProperties.Setter()
.withMetricsRollingStatisticalWindowBuckets(int value)
參數 | 作用 | 備註 |
---|---|---|
circuitBreaker.errorThresholdPercentage | 失敗率達到多少百分比後熔斷 | 默認值:50 主要根據依賴重要性進行調整 |
circuitBreaker.forceClosed | 是否強制關閉熔斷 | 如果是強依賴,應該設置爲true |
circuitBreaker.requestVolumeThreshold | 熔斷觸發的最小個數/10s | 默認值:20 |
circuitBreaker.sleepWindowInMilliseconds | 熔斷多少秒後去嘗試請求 | 默認值:5000 |
commandKey | 默認值:當前執行方法名 | |
coreSize | 線程池coreSize | 默認值:10 |
execution.isolation.semaphore.maxConcurrentRequests | 信號量最大併發度 | SEMAPHORE模式有效,默認值:10 |
execution.isolation.strategy | 隔離策略,有THREAD和SEMAPHORE | 默認使用THREAD模式,以下幾種可以使用SEMAPHORE模式:
|
execution.isolation.thread.interruptOnTimeout | 是否打開超時線程中斷 | THREAD模式有效 |
execution.isolation.thread.timeoutInMilliseconds
| 超時時間 | 默認值:1000 在THREAD模式下,達到超時時間,可以中斷 在SEMAPHORE模式下,會等待執行完成後,再去判斷是否超時 |
execution.timeout.enabled | 是否打開超時 | |
fallback.isolation.semaphore.maxConcurrentRequests | fallback最大併發度 | 默認值:10 |
groupKey | 表示所屬的group,一個group共用線程池 | 默認值:getClass().getSimpleName(); |
maxQueueSize | 請求等待隊列 | 默認值:-1 如果使用正數,隊列將從SynchronizeQueue改爲LinkedBlockingQueue |
hystrix.command.default.metrics.rollingStats.timeInMilliseconds | 設置統計的時間窗口值的,毫秒值 | circuit break 的打開會根據1個rolling window的統計來計算。若rolling window被設爲10000毫秒,則rolling window會被分成n個buckets,每個bucket包含success,failure,timeout,rejection的次數的統計信息。默認10000 |
hystrix.command.default.metrics.rollingStats.numBuckets | 設置一個rolling window被劃分的數量 | |
hystrix.command.default.metrics.healthSnapshot.intervalInMilliseconds | 記錄health 快照(用來統計成功和錯誤綠)的間隔,默認500ms |
熔斷器:Circuit Breaker
前一節我們瞭解了Hystrix利用線程池實現了對服務的隔離。
熔斷器是位於線程池之前的組件。
用戶請求某一服務之後,Hystrix會先經過熔斷器,此時如果熔斷器的狀態是打開(跳起),則說明已經熔斷,這時將直接進行降級處理,不會繼續將請求發到線程池。
套用銀行櫃員的例子,櫃員相當於服務,窗口前排隊的是線程池,大堂經理則可以看成是熔斷器。通常的流程是:客戶進門,告訴大堂經理要辦什麼業務,這時他會判斷客戶請求的窗口是否在正常處理業務,如果正常,他就會讓客戶到該窗口排隊(也就是進入了線程池),如果不正常,他根本不會讓客戶去排隊。
熔斷器相當於在線程池之前的一層屏障。
下面來看一下熔斷器的工作原理
每個熔斷器默認維護10個bucket
每秒創建一個bucket
每個blucket記錄成功,失敗,超時,拒絕的次數
當有新的bucket被創建時,最舊的bucket會被拋棄
熔斷算法
判斷是否進行熔斷的依據是:
根據bucket中記錄的次數,計算錯誤率。
當錯誤率超過預設的值(默認是50%)且10秒內超過20個請求,則開啓熔斷。
熔斷恢復
對於被熔斷的請求,並不是永久被切斷,而是被暫停一段時間(默認是5s)之後,允許部分請求通過,若請求都是健康的(RT<250ms)則對請求健康恢復(取消熔斷),如果不是健康的,則繼續熔斷。
服務調用的各種結果(成功,異常,超時,拒絕),都會上報給熔斷器,計入bucket參與計算。