這篇文章主要介紹Spring Cloud中Hystrix功能的示例分析,文中介紹的非常詳細(xì),具有一定的參考價(jià)值,感興趣的小伙伴們一定要看完!
創(chuàng)新互聯(lián)專注于企業(yè)全網(wǎng)整合營(yíng)銷推廣、網(wǎng)站重做改版、文登網(wǎng)站定制設(shè)計(jì)、自適應(yīng)品牌網(wǎng)站建設(shè)、HTML5、商城網(wǎng)站定制開(kāi)發(fā)、集團(tuán)公司官網(wǎng)建設(shè)、外貿(mào)網(wǎng)站建設(shè)、高端網(wǎng)站制作、響應(yīng)式網(wǎng)頁(yè)設(shè)計(jì)等建站業(yè)務(wù),價(jià)格優(yōu)惠性價(jià)比高,為文登等各大城市提供網(wǎng)站開(kāi)發(fā)制作服務(wù)。
一、概述
在微服務(wù)架構(gòu)中,我們將系統(tǒng)拆分成了很多服務(wù)單元,各單元的應(yīng)用間通過(guò)服務(wù)注冊(cè)與訂閱的方式互相依賴。由于每個(gè)單元都在不同的進(jìn)程中運(yùn)行,依賴通過(guò)遠(yuǎn)程調(diào)用的方式執(zhí)行,這樣就有可能因?yàn)榫W(wǎng)絡(luò)原因或是依賴服務(wù)自身間題出現(xiàn)調(diào)用故障或延遲,而這些問(wèn)題會(huì)直接導(dǎo)致調(diào)用方的對(duì)外服務(wù)也出現(xiàn)延遲,若此時(shí)調(diào)用方的請(qǐng)求不斷增加,最后就會(huì)因等待出現(xiàn)故障的依賴方響應(yīng)形成任務(wù)積壓,最終導(dǎo)致自身服務(wù)的癱瘓。
所以我們引入了斷路器,類似于物理上的電路,當(dāng)電流過(guò)載時(shí),就斷開(kāi)電路,就是我們俗稱的“跳閘”。同理,服務(wù)間的調(diào)用也是如此,當(dāng)不斷的出現(xiàn)服務(wù)延遲、故障等影響到系統(tǒng)性能的調(diào)用,就把這個(gè)服務(wù)調(diào)用切斷!
Spring Cloud Hystrix 實(shí)現(xiàn)了斷路器、線程隔離等一系列服務(wù)保護(hù)功能。它也是基于 Net?ix 的開(kāi)源框架 Hystrix 實(shí)現(xiàn)的,該框架的目標(biāo)在于通過(guò)控制那些訪問(wèn)遠(yuǎn)程系統(tǒng)、服務(wù)和第三方庫(kù)的節(jié)點(diǎn),從而對(duì)延遲和故障提供更強(qiáng)大的容錯(cuò)能力。Hystrix 具備服務(wù)降級(jí)、服務(wù)熔斷、線程和信號(hào)隔離、請(qǐng)求緩存、請(qǐng)求合并以及服務(wù)監(jiān)控等強(qiáng)大功能。
二、Hystrix 工作流程
1.創(chuàng)建 HystrixCommand(用在依賴的服務(wù)返回單個(gè)操作結(jié)果的時(shí)候) 或 HystrixObserableCommand(用在依賴的服務(wù)返回多個(gè)操作結(jié)果的時(shí)候) 對(duì)象。
2.命令執(zhí)行。其中 HystrixComand 實(shí)現(xiàn)了下面前兩種執(zhí)行方式;而 HystrixObservableCommand 實(shí)現(xiàn)了后兩種執(zhí)行方式:
execute():同步執(zhí)行,從依賴的服務(wù)返回一個(gè)單一的結(jié)果對(duì)象, 或是在發(fā)生錯(cuò)誤的時(shí)候拋出異常。
queue():異步執(zhí)行, 直接返回 一個(gè)Future對(duì)象, 其中包含了服務(wù)執(zhí)行結(jié)束時(shí)要返回的單一結(jié)果對(duì)象。
observe():返回 Observable 對(duì)象,它代表了操作的多個(gè)結(jié)果,它是一個(gè) Hot Obserable(不論 "事件源" 是否有 "訂閱者",都會(huì)在創(chuàng)建后對(duì)事件進(jìn)行發(fā)布,所以對(duì)于 Hot Observable 的每一個(gè) "訂閱者" 都有可能是從 "事件源" 的中途開(kāi)始的,并可能只是看到了整個(gè)操作的局部過(guò)程)。
toObservable(): 同樣會(huì)返回 Observable 對(duì)象,也代表了操作的多個(gè)結(jié)果,但它返回的是一個(gè)Cold Observable(沒(méi)有 "訂閱者" 的時(shí)候并不會(huì)發(fā)布事件,而是進(jìn)行等待,直到有 "訂閱者" 之后才發(fā)布事件,所以對(duì)于 Cold Observable 的訂閱者,它可以保證從一開(kāi)始看到整個(gè)操作的全部過(guò)程)。
3.若當(dāng)前命令的請(qǐng)求緩存功能是被啟用的, 并且該命令緩存命中, 那么緩存的結(jié)果會(huì)立即以 Observable 對(duì)象的形式 返回。
4.檢查斷路器是否為打開(kāi)狀態(tài)。如果斷路器是打開(kāi)的,那么Hystrix不會(huì)執(zhí)行命令,而是轉(zhuǎn)接到 fallback 處理邏輯(第 8 步);如果斷路器是關(guān)閉的,檢查是否有可用資源來(lái)執(zhí)行命令(第 5 步)。
5.線程池/請(qǐng)求隊(duì)列/信號(hào)量是否占滿。如果命令依賴服務(wù)的專有線程池和請(qǐng)求隊(duì)列,或者信號(hào)量(不使用線程池的時(shí)候)已經(jīng)被占滿, 那么 Hystrix 也不會(huì)執(zhí)行命令, 而是轉(zhuǎn)接到 fallback 處理邏輯(第8步)。
6.Hystrix 會(huì)根據(jù)我們編寫(xiě)的方法來(lái)決定采取什么樣的方式去請(qǐng)求依賴服務(wù)。
HystrixCommand.run() :返回一個(gè)單一的結(jié)果,或者拋出異常。
HystrixObservableCommand.construct(): 返回一個(gè)Observable 對(duì)象來(lái)發(fā)射多個(gè)結(jié)果,或通過(guò) onError 發(fā)送錯(cuò)誤通知。
7.Hystrix會(huì)將 "成功"、"失敗"、"拒絕"、"超時(shí)" 等信息報(bào)告給斷路器, 而斷路器會(huì)維護(hù)一組計(jì)數(shù)器來(lái)統(tǒng)計(jì)這些數(shù)據(jù)。斷路器會(huì)使用這些統(tǒng)計(jì)數(shù)據(jù)來(lái)決定是否要將斷路器打開(kāi),來(lái)對(duì)某個(gè)依賴服務(wù)的請(qǐng)求進(jìn)行 "熔斷/短路"。
8.當(dāng)命令執(zhí)行失敗的時(shí)候, Hystrix 會(huì)進(jìn)入 fallback 嘗試回退處理, 我們通常也稱該操作為 "服務(wù)降級(jí)"。而能夠引起服務(wù)降級(jí)處理的情況有下面幾種:
第4步: 當(dāng)前命令處于"熔斷/短路"狀態(tài),斷路器是打開(kāi)的時(shí)候。
第5步: 當(dāng)前命令的線程池、 請(qǐng)求隊(duì)列或 者信號(hào)量被占滿的時(shí)候。
第6步:HystrixObservableCommand.construct() 或 HystrixCommand.run() 拋出異常的時(shí)候。
9.當(dāng)Hystrix命令執(zhí)行成功之后, 它會(huì)將處理結(jié)果直接返回或是以O(shè)bservable 的形式返回。
tips:如果我們沒(méi)有為命令實(shí)現(xiàn)降級(jí)邏輯或者在降級(jí)處理邏輯中拋出了異常, Hystrix 依然會(huì)返回一個(gè) Observable 對(duì)象, 但是它不會(huì)發(fā)射任何結(jié)果數(shù)據(jù), 而是通過(guò) onError 方法通知命令立即中斷請(qǐng)求,并通過(guò)onError()方法將引起命令失敗的異常發(fā)送給調(diào)用者。
三、Hystrix 熔斷保護(hù)機(jī)制
1.假設(shè)大量的請(qǐng)求數(shù)量超過(guò)了 HystrixCommandProperties.circuitBreakerRequestVolumeThreshold() 的閾值,熔斷器將會(huì)從關(guān)閉狀態(tài)變成打開(kāi)狀態(tài);
2.假設(shè)依賴調(diào)用失敗的百分比超過(guò)了 HystrixCommandProperties.circuitBreakerErrorThresholdPercentage() 的閾值,熔斷器將會(huì)從關(guān)閉狀態(tài)變成打開(kāi)狀態(tài);
3.在熔斷器處于打開(kāi)狀態(tài)的期間,所有對(duì)這個(gè)依賴進(jìn)行的調(diào)用都會(huì)短路,即不進(jìn)行真正的依賴調(diào)用,返回失??;
在等待(冷卻)的時(shí)間超過(guò) HystrixCommandProperties.circuitBreakerSleepWindowInMilliseconds() 的值后,熔斷器將處于半開(kāi)的狀態(tài),將允許單個(gè)請(qǐng)求去調(diào)用依賴,如果這次的依賴調(diào)用還是失敗,熔斷器狀態(tài)將再次變成打開(kāi),這個(gè)打開(kāi)狀態(tài)持續(xù)時(shí)間是
4.HystrixCommandProperties.circuitBreakerSleepWindowInMilliseconds() 配置的值;如果這次的依賴調(diào)用成功,熔斷器狀態(tài)將變成關(guān)閉,后續(xù)依賴調(diào)用可正常執(zhí)行。
四、Hystrix 依賴隔離機(jī)制
線程池隔離
Hystrix 則使用“艙壁模式”實(shí)現(xiàn)線程池的隔離,它會(huì)為每一個(gè)依賴服務(wù)創(chuàng)建 一個(gè)獨(dú)立的線程池,這樣就算某個(gè)依賴服務(wù)出現(xiàn)延遲過(guò)高的情況,也只是對(duì)該依賴服務(wù)的調(diào)用產(chǎn)生影響,而不會(huì)拖慢其他的依賴服務(wù)。缺點(diǎn)是涉及到線程切換的性能損耗,但是官方給出的結(jié)果是性能損耗是可以接受的。
信號(hào)量隔離
信號(hào)量隔離可實(shí)現(xiàn)對(duì)依賴調(diào)用最高并發(fā)請(qǐng)求數(shù)的限制,每次依賴調(diào)用都會(huì)先判斷信號(hào)量是否達(dá)到閾值,如果達(dá)到極限值則拒絕調(diào)用。信號(hào)量的開(kāi)銷遠(yuǎn)比線程池的開(kāi)銷小,但是它不能設(shè)置超時(shí)和實(shí)現(xiàn)異步訪問(wèn)。所以,只有在依賴服務(wù)是足夠可靠的情況下才使用信號(hào)量 。以下是兩種配置信號(hào)量隔離的方式:
Setter 方式
HystrixCommand.Setter setter = HystrixCommand.Setter .withGroupKey(HystrixCommandGroupKey.Factory.asKey("strGroupCommand")) .andCommandKey(HystrixCommandKey.Factory.asKey("strCommand")) .andThreadPoolKey(HystrixThreadPoolKey.Factory.asKey("strThreadPool")); // 配置信號(hào)量隔離 HystrixCommandProperties.Setter commandPropertiesSetter = HystrixCommandProperties.Setter().withExecutionIsolationStrategy(HystrixCommandProperties.ExecutionIsolationStrategy.SEMAPHORE); setter.andCommandPropertiesDefaults(commandPropertiesSetter);
注解方式
@HystrixCommand(fallbackMethod = "fallbackMethod", commandProperties = { // 設(shè)置隔離策略,THREAD 表示線程池 SEMAPHORE:信號(hào)池隔離 @HystrixProperty(name = "execution.isolation.strategy", value = "THREAD"), // 當(dāng)隔離策略選擇信號(hào)池隔離的時(shí)候,用來(lái)設(shè)置信號(hào)池的大小(最大并發(fā)數(shù)) @HystrixProperty(name = "execution.isolation.semaphore.maxConcurrentRequests", value = "10"), } )
五、hystrix 實(shí)戰(zhàn)
SpringBoot 版本號(hào):2.1.6.RELEASE
SpringCloud 版本號(hào):Greenwich.RELEASE
1. pom.xml
org.springframework.cloud spring-cloud-starter-netflix-hystrix
2. 在 SpringBoot 的啟動(dòng)類上引入 @EnableCircuitBreaker 注解,開(kāi)啟斷路器功能。
3. 上面 hystrix 工作原理中提到斷路器有四種執(zhí)行方式:
execute() - 同步執(zhí)行
@HystrixCommand(fallbackMethod = "fallbackMethod") public String strConsumer() { ResponseEntityresult = restTemplate.getForEntity("http://cloud-eureka-client/hello", String.class); return result.getBody(); }
fallbackMethod —— 回調(diào)方法,在服務(wù)調(diào)用異常、斷路器打開(kāi)、線程池/請(qǐng)求隊(duì)列/信號(hào)量占滿時(shí)會(huì)走回調(diào)邏輯。必須和服務(wù)方法定義在同一個(gè)類中,對(duì)修飾符沒(méi)有特定的要求,定義為 private、 protected、 public 均可。
queue() - 異步執(zhí)行
@HystrixCommand(fallbackMethod = "fallbackMethod", ignoreExceptions = {IllegalAccessException.class}) public FutureasyncStrConsumer() { Future asyncResult = new AsyncResult () { @Override public String invoke() { ResponseEntity result = restTemplate.getForEntity("http://cloud-eureka-client/hello", String.class); return result.getBody(); } }; return asyncResult; }
ignoreExceptions 表示拋出該異常時(shí)不走降級(jí)回調(diào)邏輯,忽略此異常。
observe () 執(zhí)行方式
@HystrixCommand(observableExecutionMode = ObservableExecutionMode.EAGER) protected Observableconstruct() { ResponseEntity result = restTemplate.getForEntity("http://cloud-eureka-client/hello", String.class); return Observable.just(result.getBody()); }
toObservable() 執(zhí)行方式
@HystrixCommand(observableExecutionMode = ObservableExecutionMode.LAZY) protected Observableconstruct() { ResponseEntity result = restTemplate.getForEntity("http://cloud-eureka-client/hello", String.class); return Observable.just(result.getBody()); }
4. 命令名稱、分組以及線程池劃分
Hystrix 會(huì)根據(jù)組來(lái)組織和統(tǒng)計(jì)命令的告警、儀表盤(pán)等信息。
默認(rèn)情況下,Hystrix 會(huì)讓相同組名的命令使用同一個(gè)線程池。
通常情況下,盡量通過(guò) HystrixThreadPoolKey 的方式來(lái)指定線程池的劃分,而不是通過(guò)組名的默認(rèn)方式實(shí)現(xiàn)劃分,因?yàn)槎鄠€(gè)不同的命令可能從業(yè)務(wù)邏輯上來(lái)看屬于同一個(gè)組,但是往往從實(shí)現(xiàn)本身上需要跟其他命令進(jìn)行隔離。
@HystrixCommand(fallbackMethod = "fallbackMethod", groupKey = "strGroupCommand", commandKey = "strCommand", threadPoolKey = "strThreadPool") public String strConsumer(@CacheKey Long id) { ResponseEntityresult = restTemplate.getForEntity("http://cloud-eureka-client/hello", String.class); return result.getBody(); }
groupKey 默認(rèn)是類名,commandKey 默認(rèn)是方法名 ,threadPoolKey 默認(rèn)和 groupKey 一致。
5. 請(qǐng)求緩存和請(qǐng)求合并
5.1 請(qǐng)求緩存
緩存的作用和好處,真的是無(wú)需多言了。請(qǐng)求緩存,顧名思義,就是將對(duì)同一個(gè) key 的請(qǐng)求結(jié)果,緩存下來(lái)。那么下次對(duì)這個(gè) key 的請(qǐng)求,數(shù)據(jù)就直接在緩存中返回,減少響應(yīng)時(shí)間;
在 Hystrix 中使用緩存,主要是三個(gè)注解:@CacheResult、@CacheKey、@CacheRemove
@CacheResult:用來(lái)標(biāo)記請(qǐng)求結(jié)果應(yīng)該被緩存,必須與 @HystrixCommand 一起使用。
@CacheKey:用來(lái)修飾方法參數(shù),表示緩存的 key 名,優(yōu)先級(jí)高于 @CacheResult 設(shè)置的 key 名。
@CacheRemove:當(dāng)數(shù)據(jù)更新的時(shí)候,為了數(shù)據(jù)的一致性,我們需要使緩存失效。@CacheRemove 就是用來(lái)標(biāo)記請(qǐng)求結(jié)果的緩存失效(commandKey 是必填參數(shù),表示要失效的緩存 key)。
@CacheResult(cacheKeyMethod = "getCacheKey") @HystrixCommand(fallbackMethod = "fallbackMethod") public String strConsumer(@CacheKey Long id) { ResponseEntityresult = restTemplate.getForEntity("http://cloud-eureka-client/hello", String.class); return result.getBody(); }
5.2 請(qǐng)求合并
微服務(wù)架構(gòu)中的依賴通常通過(guò)遠(yuǎn)程調(diào)用實(shí)現(xiàn),而遠(yuǎn)程調(diào)用中最常見(jiàn)的問(wèn)題就是通信消耗與連接數(shù)占用。
在高并發(fā)的情況之下,因通信次數(shù)的增加,總的通信時(shí)間消耗將會(huì)變得不那么理想。同時(shí),因?yàn)橐蕾嚪?wù)的線程池資源有限,將出現(xiàn)排隊(duì)等待與響應(yīng)延遲的清況。為了優(yōu)化這兩個(gè)問(wèn)題,Hystrix 提供了 HystrixCollapser 來(lái)實(shí)現(xiàn)請(qǐng)求的合并,以減少通信消耗和線程數(shù)的占用。
@RestController public class UserConsumer { @Autowired private UserService userService; /** * 通過(guò) id 獲取用戶接口 * * @param id * @return */ @HystrixCollapser(batchMethod = "getByIds", collapserProperties = { // 10ms 內(nèi)的請(qǐng)求合并為一次批量請(qǐng)求 @HystrixProperty(name = "timerDelayInMilliseconds", value = "10"), // 批處理過(guò)程中是否開(kāi)啟緩存 @HystrixProperty(name = "requestCache.enabled", value = "10"), }) public String getById(Long id) { return userService.getUserById(id); } /** * 通過(guò) ids 批量獲取用戶信息接口 * * @param ids id 集合 * @return */ @HystrixCommand public SetgetByIds(List ids) { return userService.getUserByIds(ids); } }
雖然通過(guò)請(qǐng)求合并可以減少請(qǐng)求的數(shù)量以緩解依賴服務(wù)線程池的資源,但是在使用的時(shí)候也需要注意它所帶來(lái)的額外開(kāi)銷:用于請(qǐng)求合并的延遲時(shí)間窗會(huì)使得依賴服務(wù)的請(qǐng)求延遲增高。
是否開(kāi)啟緩存合并,我們一般考慮下面兩個(gè)因素:
如果依賴服務(wù)的請(qǐng)求命令本身是一個(gè)高延遲的命令,那么可以使用請(qǐng)求合并器,因?yàn)楦哐舆t,時(shí)間窗的時(shí)間消耗顯得微不足道了。
如果一個(gè)時(shí)間窗內(nèi)只有1-2個(gè)請(qǐng)求,那么這樣的依賴服務(wù)不適合使用請(qǐng)求合并器。這種情況不但不能提升系統(tǒng)性能,反而會(huì)成為系統(tǒng)瓶頸;相反,如果一個(gè)時(shí)間窗內(nèi)具有很高的并發(fā)量,并且服務(wù)提供方也實(shí)現(xiàn)了批量處理接口,那么使用請(qǐng)求合并器可以有效減少網(wǎng)絡(luò)連接數(shù)量并極大提升系統(tǒng)吞吐量。
6. HystrixCommand 屬性介紹
@HystrixCommand(fallbackMethod = "fallbackMethod", groupKey = "strGroupCommand", commandKey = "strCommand", threadPoolKey = "strThreadPool", commandProperties = { // 設(shè)置隔離策略,THREAD 表示線程池 SEMAPHORE:信號(hào)池隔離 @HystrixProperty(name = "execution.isolation.strategy", value = "THREAD"), // 當(dāng)隔離策略選擇信號(hào)池隔離的時(shí)候,用來(lái)設(shè)置信號(hào)池的大?。ㄗ畲蟛l(fā)數(shù)) @HystrixProperty(name = "execution.isolation.semaphore.maxConcurrentRequests", value = "10"), // 配置命令執(zhí)行的超時(shí)時(shí)間 @HystrixProperty(name = "execution.isolation.thread.timeoutinMilliseconds", value = "10"), // 是否啟用超時(shí)時(shí)間 @HystrixProperty(name = "execution.timeout.enabled", value = "true"), // 執(zhí)行超時(shí)的時(shí)候是否中斷 @HystrixProperty(name = "execution.isolation.thread.interruptOnTimeout", value = "true"), // 執(zhí)行被取消的時(shí)候是否中斷 @HystrixProperty(name = "execution.isolation.thread.interruptOnCancel", value = "true"), // 允許回調(diào)方法執(zhí)行的最大并發(fā)數(shù) @HystrixProperty(name = "fallback.isolation.semaphore.maxConcurrentRequests", value = "10"), // 服務(wù)降級(jí)是否啟用,是否執(zhí)行回調(diào)函數(shù) @HystrixProperty(name = "fallback.enabled", value = "true"), // 是否啟用斷路器 @HystrixProperty(name = "circuitBreaker.enabled", value = "true"), // 該屬性用來(lái)設(shè)置在滾動(dòng)時(shí)間窗中,斷路器熔斷的最小請(qǐng)求數(shù)。例如,默認(rèn)該值為 20 的時(shí)候,如果滾動(dòng)時(shí)間窗(默認(rèn)10秒)內(nèi)僅收到了19個(gè)請(qǐng)求, 即使這19個(gè)請(qǐng)求都失敗了,斷路器也不會(huì)打開(kāi)。 @HystrixProperty(name = "circuitBreaker.requestVolumeThreshold", value = "20"), // 該屬性用來(lái)設(shè)置在滾動(dòng)時(shí)間窗中,表示在滾動(dòng)時(shí)間窗中,在請(qǐng)求數(shù)量超過(guò) circuitBreaker.requestVolumeThreshold 的情況下,如果錯(cuò)誤請(qǐng)求數(shù)的百分比超過(guò)50, 就把斷路器設(shè)置為 "打開(kāi)" 狀態(tài),否則就設(shè)置為 "關(guān)閉" 狀態(tài)。 @HystrixProperty(name = "circuitBreaker.errorThresholdPercentage", value = "50"), // 該屬性用來(lái)設(shè)置當(dāng)斷路器打開(kāi)之后的休眠時(shí)間窗。 休眠時(shí)間窗結(jié)束之后,會(huì)將斷路器置為 "半開(kāi)" 狀態(tài),嘗試熔斷的請(qǐng)求命令,如果依然失敗就將斷路器繼續(xù)設(shè)置為 "打開(kāi)" 狀態(tài),如果成功就設(shè)置為 "關(guān)閉" 狀態(tài)。 @HystrixProperty(name = "circuitBreaker.sleepWindowinMilliseconds", value = "5000"), // 斷路器強(qiáng)制打開(kāi) @HystrixProperty(name = "circuitBreaker.forceOpen", value = "false"), // 斷路器強(qiáng)制關(guān)閉 @HystrixProperty(name = "circuitBreaker.forceClosed", value = "false"), // 滾動(dòng)時(shí)間窗設(shè)置,該時(shí)間用于斷路器判斷健康度時(shí)需要收集信息的持續(xù)時(shí)間 @HystrixProperty(name = "metrics.rollingStats.timeinMilliseconds", value = "10000"), // 該屬性用來(lái)設(shè)置滾動(dòng)時(shí)間窗統(tǒng)計(jì)指標(biāo)信息時(shí)劃分"桶"的數(shù)量,斷路器在收集指標(biāo)信息的時(shí)候會(huì)根據(jù)設(shè)置的時(shí)間窗長(zhǎng)度拆分成多個(gè) "桶" 來(lái)累計(jì)各度量值,每個(gè)"桶"記錄了一段時(shí)間內(nèi)的采集指標(biāo)。 // 比如 10 秒內(nèi)拆分成 10 個(gè)"桶"收集這樣,所以 timeinMilliseconds 必須能被 numBuckets 整除。否則會(huì)拋異常 @HystrixProperty(name = "metrics.rollingStats.numBuckets", value = "10"), // 該屬性用來(lái)設(shè)置對(duì)命令執(zhí)行的延遲是否使用百分位數(shù)來(lái)跟蹤和計(jì)算。如果設(shè)置為 false, 那么所有的概要統(tǒng)計(jì)都將返回 -1。 @HystrixProperty(name = "metrics.rollingPercentile.enabled", value = "false"), // 該屬性用來(lái)設(shè)置百分位統(tǒng)計(jì)的滾動(dòng)窗口的持續(xù)時(shí)間,單位為毫秒。 @HystrixProperty(name = "metrics.rollingPercentile.timeInMilliseconds", value = "60000"), // 該屬性用來(lái)設(shè)置百分位統(tǒng)計(jì)滾動(dòng)窗口中使用 “ 桶 ”的數(shù)量。 @HystrixProperty(name = "metrics.rollingPercentile.numBuckets", value = "60000"), // 該屬性用來(lái)設(shè)置在執(zhí)行過(guò)程中每個(gè) “桶” 中保留的最大執(zhí)行次數(shù)。如果在滾動(dòng)時(shí)間窗內(nèi)發(fā)生超過(guò)該設(shè)定值的執(zhí)行次數(shù), // 就從最初的位置開(kāi)始重寫(xiě)。例如,將該值設(shè)置為100, 滾動(dòng)窗口為10秒,若在10秒內(nèi)一個(gè) “桶 ”中發(fā)生了500次執(zhí)行, // 那么該 “桶” 中只保留 最后的100次執(zhí)行的統(tǒng)計(jì)。另外,增加該值的大小將會(huì)增加內(nèi)存量的消耗,并增加排序百分位數(shù)所需的計(jì)算時(shí)間。 @HystrixProperty(name = "metrics.rollingPercentile.bucketSize", value = "100"), // 該屬性用來(lái)設(shè)置采集影響斷路器狀態(tài)的健康快照(請(qǐng)求的成功、 錯(cuò)誤百分比)的間隔等待時(shí)間。 @HystrixProperty(name = "metrics.healthSnapshot.intervalinMilliseconds", value = "500"), // 是否開(kāi)啟請(qǐng)求緩存 @HystrixProperty(name = "requestCache.enabled", value = "true"), // HystrixCommand的執(zhí)行和事件是否打印日志到 HystrixRequestLog 中 @HystrixProperty(name = "requestLog.enabled", value = "true"), }, threadPoolProperties = { // 該參數(shù)用來(lái)設(shè)置執(zhí)行命令線程池的核心線程數(shù),該值也就是命令執(zhí)行的最大并發(fā)量 @HystrixProperty(name = "coreSize", value = "10"), // 該參數(shù)用來(lái)設(shè)置線程池的最大隊(duì)列大小。當(dāng)設(shè)置為 -1 時(shí),線程池將使用 SynchronousQueue 實(shí)現(xiàn)的隊(duì)列,否則將使用 LinkedBlockingQueue 實(shí)現(xiàn)的隊(duì)列。 @HystrixProperty(name = "maxQueueSize", value = "-1"), // 該參數(shù)用來(lái)為隊(duì)列設(shè)置拒絕閾值。 通過(guò)該參數(shù), 即使隊(duì)列沒(méi)有達(dá)到最大值也能拒絕請(qǐng)求。 // 該參數(shù)主要是對(duì) LinkedBlockingQueue 隊(duì)列的補(bǔ)充,因?yàn)?nbsp;LinkedBlockingQueue 隊(duì)列不能動(dòng)態(tài)修改它的對(duì)象大小,而通過(guò)該屬性就可以調(diào)整拒絕請(qǐng)求的隊(duì)列大小了。 @HystrixProperty(name = "queueSizeRejectionThreshold", value = "5"), } ) public String strConsumer() { ResponseEntityresult = restTemplate.getForEntity("http://cloud-eureka-client/hello", String.class); return result.getBody(); }
以上是“Spring Cloud中Hystrix功能的示例分析”這篇文章的所有內(nèi)容,感謝各位的閱讀!希望分享的內(nèi)容對(duì)大家有幫助,更多相關(guān)知識(shí),歡迎關(guān)注創(chuàng)新互聯(lián)行業(yè)資訊頻道!