Hystrix是一个用于处理分布式系统的延迟和容错的开源库,在分布式系统里,许多依赖不可避免的会调用失败,比如超时、异常等,Hystrix能够保证在一个依赖出问题的情况下,不会导致整体服务失败,避免级联故障,以提高分布式系统的弹性。
“断路器”本身是一种开关装置,当某个服务单元发生故障之后,通过断路器的故障监控(类似熔断保险丝),向调用方返回一个符合预期的、可处理的备选响应(FallBack),而不是长时间的等待或者抛出调用方无法处理的异常,这样就保证了服务调用方的线程不会被长时间、不必要地占用,从而避免了故障在分布式系统中的蔓延,乃至雪崩。
服务压力剧增的时候根据当前的业务情况及流量对一些服务和页面有策略的降级,以此环节服务器的压力,以保证核心任务的进行。
同时保证部分甚至大部分任务客户能得到正确的相应。也就是当前的请求处理不了了或者出错了,给一个默认的返回。
服务熔断:在股票市场,熔断这个词大家都不陌生,是指当股指波幅达到某个点后,交易所为控制风险采取的暂停交易措施。相应的,服务熔断一般是指软件系统中,由于某些原因使得服务出现了过载现象,为防止造成整个系统故障,从而采用的一种保护措施,所以很多地方把熔断亦称为过载保护。
服务失败-> 服务的降级 -> 进而熔断 -> 恢复调用链路
限流的目的是通过对并发访问/请求进行限速或者一个时间窗口内的的请求进行限速来保护系统,一旦达到限制速率则可以拒绝服务(定向到错误页或告知资源没有了)、排队或等待(比如秒杀、评论、下单)、降级(返回兜底数据或默认数据,如商品详情页库存默认有货)。
多个微服务之间调用的时候,假设微服务A调用微服务B和微服务C,微服务B和微服务C又调用其他的微服务,这就是所谓的“扇出”。如果扇出的链路上某个微服务的调用响应时间过长或者不可用,对微服务A的调用就会占用越来越多的系统资源,进而引起系统崩溃,这就是所谓的“雪崩效应”。
新建两个方法来测试在没有使用服务降级等情况下,系统在高并发环境下的情况
cloud-provider-hystrix-payment8001
org.springframework.cloud
spring-cloud-starter-netflix-hystrix
org.springframework.cloud
spring-cloud-starter-netflix-eureka-client
com.lejia.springcloud
cloud-api-commons
${project.version}
org.springframework.boot
spring-boot-starter-web
org.springframework.boot
spring-boot-starter-actuator
org.springframework.boot
spring-boot-devtools
runtime
true
org.projectlombok
lombok
1.18.16
org.springframework.boot
spring-boot-starter-test
test
org.springframework.boot
spring-boot-devtools
runtime
true
server:
port: 8001
spring:
application:
name: cloud-payment-hystrix-payment
eureka:
client:
#表示是否将自己注册进EurekaServer默认为true
register-with-eureka: true
#是否从EurekaServe抓取已有的注册信息,默认为true
# 单节点无所谓,集群必须设置为true才能配合ribbon使用负载均衡
fetch-registry: true
service-url:
defaultZone: http://localhost:7001/eureka
## 集群版
# defaultZone: http://eureka7001.com:7001/eurekaka,http://eureka7003.com:7003/eureka
@SpringBootApplication
@EnableDiscoveryClient
public class PaymentHystrixMain8001 {
public static void main(String[] args) {
SpringApplication.run(PaymentHystrixMain8001.class, args);
}
}
package com.lejia.springcloud.service;
新建PaymentService.java
新建两个方法,一个是延时3秒后返回数据,一个是立即返回数据,测试在高并发的情况下系统的性能
public class PaymentService {
public String paymentInto_OK(Integer id){
return "线程池\t"+Thread.currentThread().getName()+"\tpaymentInto_OK\t" + id + "\tO(∩_∩)O哈哈~";
}
public String paymentInto_Timeout(Integer id){
int time = 3;
try {
TimeUnit.SECONDS.sleep(time);
} catch (InterruptedException e) {
e.printStackTrace();
}
return "线程池\t"+Thread.currentThread().getName()+"\tpaymentInto_Timeout\t" + id + "\t┭┮﹏┭┮,超时,超时"+time+"s";
}
}
package com.lejia.springcloud.controller;
PaymentController.java
@RestController
@Slf4j
@RequestMapping("/payment/hystrix")
public class PaymentController {
@Resource
private PaymentService paymentService;
@Value("${server.port}")
private String serverPort;
@GetMapping("/ok/{id}")
public String paymentInfo_OK(@PathVariable("id") Integer id){
String result = paymentService.paymentInto_OK(id);
log.info("************ result: "+result);
return result;
}
@GetMapping("/timeout/{id}")
public String paymentInfo_Timeout(@PathVariable("id") Integer id){
String result = paymentService.paymentInto_Timeout(id);
log.info("************ result: "+result);
return result;
}
}
http://localhost:8001/payment/hystrix/ok/222
立刻显示在页面中
http://localhost:8001/payment/hystrix/timeout/111
超时3s后显示在页面中
为了进行高并发测试,我们下载Jmeter软件来进行一下测试
进入官网
https://jmeter.apache.org/
windows选择zip包
下载解压
进入apache-jmeter-5.3文件夹下的bin目录
找到 jmeter.bat,双击打开即可
桌面会立刻打开一个命令行窗口,里面运行的是jmeter的后台程序,稍等片刻会弹出jmeter应用窗口
初始界面是英语的,我们可以选择一下语言
http压力测试
右击测试计划 -> 添加 -> 线程 - > 线程组
输入线程组名称 选择
CTRL + S 保存
选择刚才新建的线程组
右击 线程组2w测试 -> 添加 -> 取样器 -> HTTP 请求
CTRL +S 保存 我选择保存在了 jmx中
点击启动开启压力测试
然后进入程序后台可以看到压力测试正在进行中
点击 × 取消按钮即可取消当前测试
测试上一个案例
当20000个请求发给http://localhost:8001/payment/hystrix/timeout/1时,我们能够看到,tomcat将线程池的资源全部用来处理timeout的这个方法的请求。
此时我们访问无延时的请求http://localhost:8001/payment/hystrix/ok/111,系统也会出现 短暂的响应后才返回数据
相信你看到现在可能会有一点疑惑,上述的测试并没有什么明显的效果啊,我们在实际生产环境中,在大量并发的请求以及带宽的影响下,服务端的响应速度急剧上升,此时我们就需要进行一些优化,处理。此时就用到了Hystrix的服务降级功能。我们将在下述案例中进行测试
服务器忙,请稍后再试,不让客户端等待并立刻返回一个友好提示,Fallback
Hystrix一般用在消费者(客户端),但是在服务端也是可以用的
@HystrixCommand(fallbackMethod = “” , commandProperties = {})
fallbackMethod 服务降级切换的方法名称
commandProperties 配置详解
当请求服务失败并抛出了错误信息后,会自动调用@HystrixCommand标注好的fallbackMethod调用指定方法
当前服务只要不可用了就会做服务降级,降到兜底服务
我们继续使用8001来做我们的测试服务
@SpringBootApplication
@EnableDiscoveryClient
@EnableCircuitBreaker //开启断路器
public class PaymentHystrixMain8001 {
public static void main(String[] args) {
SpringApplication.run(PaymentHystrixMain8001.class, args);
}
}
package com.lejia.springcloud.service;
我们已经创建了两个测试方法
一个方法正常返回测试字符串
另一个方法等待n秒后返回字符串
现在我们新建一个服务降级方法,当我们提供的服务出现异常或者超时时,hystrix会自动将当前线程切换到我们设置的降级服务中
@HystrixCommand说明
fallbackMethod 服务降级切换的方法名称
commandProperties 配置详解 https://www.jianshu.com/p/39763a0bd9b8
@Service
public class PaymentService {
public String paymentInto_OK(Integer id){
return "线程池\t"+Thread.currentThread().getName()+"\tpaymentInto_OK\t" + id + "\tO(∩_∩)O哈哈~";
}
/**
* @HystrixCommand说明
* fallbackMethod 服务降级切换的方法名称
* commandProperties 配置详解
* https://www.jianshu.com/p/39763a0bd9b8
*/
@HystrixCommand(fallbackMethod = "paymentInfo_TimeOutHandler",
commandProperties = @HystrixProperty(name = "execution.isolation.thread.timeoutInMilliseconds",value = "5000"))
public String paymentInto_Timeout(Integer id){
int time = 3;
try {
TimeUnit.SECONDS.sleep(time);
} catch (InterruptedException e) {
e.printStackTrace();
}
return "线程池\t"+Thread.currentThread().getName()+"\tpaymentInto_Timeout\t" + id + "┭┮﹏┭┮,超时"+time+"s";
}
public String paymentInfo_TimeOutHandler(Integer id){
return "线程池\t"+Thread.currentThread().getName()+"\tpaymentInto_Timeout\t" + id + "\t8001系统服务提供出错,或者请求超时了,此方法为降级方法";
}
}
fallback设置等待时间为5s,系统响应等待3s
测试
http://localhost:8001/payment/hystrix/timeout/3
结果:
当我们的等待时间设置小于我们熔断器所设置的最大等待时间时,我们真实所需的业务被正常的响应到客户端
fallback设置等待时间为5s,系统响应等待10s
再次测试
http://localhost:8001/payment/hystrix/timeout/3
结果
测试发现,当页面响应5s后,就立刻停止了响应,转而返回给客户端降级后的服务
我们再观察一下输出日志
可以看到,我们的等待被hystrix给打断了,所以能够在等待之前切换到降级服务中
前面已经介绍过了服务端的服务降级配置。而客户端与服务端的配置也是大同小异,我们在项目开发时,一般都将服务降级设置在客户端来进行调控。
cloud-consumer-feign-hystrix-order80
我们使用open feign来进行远程服务的调用
org.springframework.cloud
spring-cloud-starter-netflix-hystrix
org.springframework.cloud
spring-cloud-starter-openfeign
org.springframework.cloud
spring-cloud-starter-netflix-eureka-client
com.lejia.springcloud
cloud-api-commons
${project.version}
org.springframework.boot
spring-boot-starter-web
org.springframework.boot
spring-boot-starter-actuator
org.springframework.boot
spring-boot-devtools
runtime
true
org.projectlombok
lombok
true
org.springframework.boot
spring-boot-starter-test
test
server:
port: 80
eureka:
client:
#表示是否将自己注册进EurekaServer默认为true
register-with-eureka: false
#是否从EurekaServe抓取已有的注册信息,默认为true
# 单节点无所谓,集群必须设置为true才能配合ribbon使用负载均衡
fetch-registry: true
service-url:
defaultZone: http://localhost:7001/eureka
# 设置feign客户端超时时间(OpenFeign默认支持ribbon)
ribbon:
# 指的是建立连接所用的时间,适用于网络状态正常的情况下,两端连接所用的时间
ReadTimeout: 5000
# 指的是建立连接后从服务器读取到可用资源所用的时间
ConnectTimeout: 5000
@SpringBootApplication
@EnableFeignClients //开启feign
@EnableDiscoveryClient //开启服务发现
@EnableHystrix //开启hystrix 继承了@EnableCircuitBreaker
public class OrderHystrixOrderMain80 {
public static void main(String[] args) {
SpringApplication.run(OrderHystrixOrderMain80.class, args);
}
}
因为我们使用的是feign来进行远程访问,所以我们新建一个接口来存放服务端提供的方法
package com.lejia.springcloud.service;
PaymentHystrixService是一个接口,里面存放的服务端暴露的接口,我们在这里需要进行远程访问所必备的接口
@Component
@FeignClient(value = "CLOUD-PAYMENT-HYSTRIX-PAYMENT")
public interface PaymentHystrixService {
@GetMapping("/payment/hystrix/ok/{id}")
public String paymentInfo_OK(@PathVariable("id") Integer id);
@GetMapping("/payment/hystrix/timeout/{id}")
public String paymentInfo_Timeout(@PathVariable("id") Integer id);
}
package com.lejia.springcloud.controller;
OrderHystrixController.java 业务类,我们真正暴露给用户的接口
hystrix我们一般都用在客户端,所以我们在controller中来设置一下我们的服务降级程序
@RestController
@Slf4j
public class OrderHystrixController {
@Resource
private PaymentHystrixService paymentHystrixService;
@GetMapping("/consumer/payment/hystrix/ok/{id}")
public String paymentInfo_OK(@PathVariable("id") Integer id){
return paymentHystrixService.paymentInfo_OK(id);
}
@GetMapping("/consumer/payment/hystrix/timeout/{id}")
@HystrixCommand(fallbackMethod = "paymentInfo_TimeOutHandler",
commandProperties = @HystrixProperty(name = "execution.isolation.thread.timeoutInMilliseconds",value = "2000"))
public String paymentInfo_Timeout(@PathVariable("id") Integer id){
return paymentHystrixService.paymentInfo_Timeout(id);
}
public String paymentInfo_TimeOutHandler(Integer id){
return "我是80的服务降级,系统响应的时间过久,已切换到我来执行";
}
}
现在我们的这个服务注册中心已经集成了一个服务提供者和一个服务消费者,因为涉及到一些时间问题所以我们先在测试之前说清楚一下,然后再进行验证
80客户端
feign
客户端连接+未收到响应 10s后 ,客户端报超时错误
# 指的是建立连接所用的时间,适用于网络状态正常的情况下,两端连接所用的时间
ReadTimeout: 5000
# 指的是建立连接后从服务器读取到可用资源所用的时间
ConnectTimeout: 5000
熔断器hystrix
客户端超时等待2秒后未收到响应,hystrix打断sleep进行服务降级
@HystrixProperty(name = "execution.isolation.thread.timeoutInMilliseconds",value = "2000")
8001服务端
服务端延迟等待3s后再返回数据给客户端
public String paymentInto_Timeout(Integer id){
int time = 3;
try {
TimeUnit.SECONDS.sleep(time);
} catch (InterruptedException e) {
e.printStackTrace();
}
熔断器hystrix
服务端响应超时等待5秒后服务降级
commandProperties = @HystrixProperty(name = "execution.isolation.thread.timeoutInMilliseconds",value = "5001"))
测试一:
客户端hystrix 2s feign 5s 服务端 sleep 3s hystrix5s
结果:
此时因为客户端的响应等待时间 2S < 服务端 睡眠等待的3s,所以一定返回客户端的服务降级方法
页面等待2s后显示
测试二:
客户端hystrix 4s feign5+5s 服务端 sleep 3s hystrix5s
结果:
页面等待3s后显示
测试三:
客户端hystrix 4s feign 5+5s 服务端 sleep 3s hystrix2s
结果:
页面等待2s后显示
测试四:
客户端hystrix 4s feign1+1 s 服务端 sleep 3s hystrix2s
结果:
页面等待2s后显示
我们在客户端使用服务降级时,需要配置降级方法,但是不可能每一个方法都需要手动的设置一个降级方法,这样就极大的耽误了开发的进度,并且造成了代码膨胀,所以我们使用hystrix提供的默认降级方法来进行统一配置。
配置方法
/**
* 全局fallback方法
* 不能有参数
* @return
*/
public String payment_Global_FallbackMethod(){
return "Global异常信息处理,请稍后再试 (キ`゚Д゚´)!!";
}
@DefaultProperties(defaultFallback = "payment_Global_FallbackMethod")
@RestController
@Slf4j
@DefaultProperties(defaultFallback = "payment_Global_FallbackMethod")
public class OrderHystrixController {
@Resource
private PaymentHystrixService paymentHystrixService;
@GetMapping("/consumer/payment/hystrix/ok/{id}")
@HystrixCommand
public String paymentInfo_OK(@PathVariable("id") Integer id){
return paymentHystrixService.paymentInfo_OK(id);
}
@GetMapping("/consumer/payment/hystrix/timeout/{id}")
@HystrixCommand(fallbackMethod = "paymentInfo_TimeOutHandler",
commandProperties = @HystrixProperty(name = "execution.isolation.thread.timeoutInMilliseconds",value = "2000"))
// @HystrixCommand
public String paymentInfo_Timeout(@PathVariable("id") Integer id){
return paymentHystrixService.paymentInfo_Timeout(id);
}
public String paymentInfo_TimeOutHandler(Integer id){
return "我是80的服务降级,系统响应的时间过久,已切换到我来执行";
}
/**
* 全局fallback方法
* 不能有参数
* @return
*/
public String payment_Global_FallbackMethod(){
return "Global异常信息处理,请稍后再试 (キ`゚Д゚´)!!";
}
}
请求ok http://localhost/consumer/payment/hystrix/ok/111
结果:
正确响应到了服务端的数据
请求timeout http://localhost/consumer/payment/hystrix/timeout/111
结果 : 因为在timeout上设置了服务降级的方法,根据就近原则会使用最近的服务降级方法
服务端宕机后(关闭8081服务)
请求ok http://localhost/consumer/payment/hystrix/ok/111
结果:
客户端响应1s后 (@HystrixCommand 默认设置的超时时间为1s),跳转到服务降级全局处理方法中
请求timeout http://localhost/consumer/payment/hystrix/timeout/111
结果:
客户端响应2s后 (@HystrixCommand自定义设置的超时时间为2s),跳转到服务降级指定处理方法中
当我们使用feign远程调用服务时,我们需要创建了一个服务接口。
接口中其中存放着我们所调用的所有服务端的方法。所以我们可以新建一个类来继承这个接口,然后使用feign提供的注解来配置接口统配降级服务。
即接口中的每个方法都默认实现了降级服务。
feign:
hystrix:
enabled: true
#如果为真,OpenFeign客户端将被Hystrix断路器包裹。
在客户端80的package com.lejia.springcloud.service;
新建PaymentFallbackService.java
@Component
public class PaymentFallbackService implements PaymentHystrixService{
@Override
public String paymentInfo_OK(Integer id) {
return "------PaymentFallbackService fall back paymentInfo_OK ┭┮﹏┭┮ ";
}
@Override
public String paymentInfo_Timeout(Integer id) {
return "------PaymentFallbackService fall back paymentInfo_Timeout ┭┮﹏┭┮ ";
}
}
在PaymentHystrixService接口中添加@FeignClient中的属性
@FeignClient(value = "CLOUD-PAYMENT-HYSTRIX-PAYMENT",fallback = PaymentFallbackService.class)
服务端宕机后(关闭8081服务)
请求ok http://localhost/consumer/payment/hystrix/ok/111
结果:
客户端响应1s后 (@HystrixCommand 默认设置的超时时间为1s),跳转到服务降级统配处理方法中
请求timeout http://localhost/consumer/payment/hystrix/timeout/111
结果:
客户端响应2s后 (@HystrixCommand自定义设置的超时时间为2s),跳转到服务降级指定处理方法中
服务降级方法的顺序
自定义fallback -> 继承接口统一配置服务降级方法 -> 默认全局fallback
熔断机制是应对雪崩效应的一种微服务链路保护机制。
当扇出链路的某个微服务出错不可用或者响应时间太长时,会进行服务的降级,进而熔断该节点微服务的调用,快速返回错误的响应信息。当检测到该节点微服务调用响应正常后,恢复调用链路。
在Spring Cloud框架里,熔断机制通过Hystrix实现。
Hystrix会监控微服务间调用的状况,但失败的调用到一定阈值,缺省是5秒内20次调用失败,就会启动熔断机制,熔断机制的注解是@HystrixCommand。
https://martinfowler.com/bliki/CircuitBreaker.html
我们在8001服务提供者模块中进行配置
在主启动上添加注解
@EnableCircuitBreaker //开启断路器即服务熔断
在service中添加两个新的测试方法
//服务熔断
@HystrixCommand(fallbackMethod = "paymentCircuitBreaker_fallback",commandProperties = {
@HystrixProperty(name = "circuitBreaker.enabled",value = "true"), //是否开启断路器
@HystrixProperty(name = "circuitBreaker.requestVolumeThreshold",value = "10"), //请求次数
@HystrixProperty(name = "circuitBreaker.sleepWindowInMilliseconds",value = "10000"), //时间窗口期
@HystrixProperty(name = "circuitBreaker.errorThresholdPercentage",value = "60") //失败率达到多少后跳闸此时进行服务降级
}
) //测试方法
public String paymentCircuitBreaker(Integer id) {
if (id < 0) {
throw new RuntimeException("##########id不能为负数###########");
}
String serialNumber = IdUtil.simpleUUID();
return Thread.currentThread().getName() + "\t" + "调用成功,流水号为 :" + serialNumber;
}
//服务降级方法
public String paymentCircuitBreaker_fallback(Integer id){
return "id不能为负数,请稍后再试 ┭┮﹏┭┮ id :" + id;
}
在controller中添加一个新的方法
//==服务熔断
@GetMapping("/circuit/{id}")
public String paymentCircuitBreaker(@PathVariable("id") Integer id){
String result = paymentService.paymentCircuitBreaker(id);
log.info("************ result: "+result);
return result;
}
http://localhost:8001/payment/hystrix/circuit/1
刷新n次都不会出现熔断现象
http://localhost:8001/payment/hystrix/circuit/-10
刷新大于6次后
再次输入无异常的测试
http://localhost:8001/payment/hystrix/circuit/2
我们可以看到,hystrix熔断功能有了效果。
此时我们需要等待窗口期时间的度过,在窗口期结束时,hystrix会先进行半熔断状态,自我恢复,测试请求是否正常,如果正常,则恢复
再次测试发现服务已经渐渐恢复了
断路器的三个重要参数:快照时间窗、请求总数阈值、错误百分比阈值
1.当满足一定的阈值的时候 (默认10内超过20个请求次数)
2.当失败率达到一定的时候 (默认10秒内超过50%的请求失败)
3.到达以上阈值,断路器将会开启
4.当开启的时候,所有请求都不会进行转发
5.一段时间之后(默认是5秒),这个时候断路器是半开状态,会让其中一个请求进行转发。如果成功,断路器会关闭,若失败,继续开启,重复4和5
再有请求调用的时候,将不会调用主逻辑,而是直接调用降级fallback。通过断路器,实现了自动地发现错误并将降级逻辑切换为主逻辑,减少响应延迟的效果。
原来的主逻辑要如何恢复呢?
对于这一问题,Hystrix也为我们实现了自动恢复功能。
当断路器打开,对主逻辑进行熔断之后,Hystrix会启动一个休眠时间窗,在这个时间窗内,降级逻辑是临时的成为主逻辑,当休眠时间窗到期,断路器将进入半打开状态,释放一次请求到原来的主逻辑上,如果此次请求正常返回,那么断路器将继续闭合,主逻辑恢复,如果此次请求依然有问题,断路器将继续进入打开状态,休眠时间窗重新计时。
配置类 HystrixCommandProperties
常用的配置说明
@HystrixCommand(fallbackMethod = "str_fallbackMethod",
groupKey = "strGroupCommand",
commandKey = "strCommand",
threadPoolKey = "strThreadPool",
commandProperties = {
//设置隔离策略,THREAD表示线程池,SEMAPHORE表示信号池隔离
@HystrixProperty(name = "execution.isolation.strategy", value = "THREAD"),
//当隔离策略选择信号池隔离的时候,用来设置信号池的大小 (最大并发数)
@HystrixProperty(name = "execution.isolation.semaphore.maxConcurrentRequests", value = "10"),
//配置命令执行的超时时间
@HystrixProperty(name = "execution.isolation.thread.timeoutinMilliseconds", value = "10"),
//是否启用超时时间
@HystrixProperty(name = "execution.timeout.enabled", value = "true"),
//执行超时的时候是否中断
@HystrixProperty(name = "execution.isolation.thread.interruptOntimeout", value = "true"),
//执行被取消的时候是否中断
@HystrixProperty(name = "execution.isolation.thread.interruptOnCancel", value = "true"),
//允许回调方法执行的最大并发数
@HystrixProperty(name = "fallback.isolation.semaphore.maxConcurrentRequests", value = "10"),
//服务降级是否开启,是否执行回调函数
@HystrixProperty(name = "fallback.enabled", value = "true"),
//是否启用断路器
@HystrixProperty(name = "circuitBreaker.enabled", value = "true"),
//该属性用来设置在滚动时间窗中,断路器熔断的最小请求数,例如,默认该值为20的时候,
//如果滚动事件窗 (默认10秒)内仅接收到了19个请求,即使这19个请求都失败了,断路器也不会打开
@HystrixProperty(name = "circuitBreaker.requestVolumeThreshold", value = "20"),
//该属性用来设置在滚动时间窗中,请求数量超过circuitBreaker.requestVolumeThreshold的情况下,
//如果错误请求数的百分比超过50%,就把断路器设置为"打开"状态,否则就设置为"关闭"状态
@HystrixProperty(name = "circuitBreaker.errorThresholdPercentage", value = "50"),
//该属性用来设置当断路器打开之后的休眠时间窗,休眠时间窗结束之后,会将断路器设置为"半开"状态,
//尝试熔断的请求命令,如果依然失败就将熔断器继续设置为"打开"状态,如果成功就设置为"关闭"状态
@HystrixProperty(name = "circuitBreaker.sleepWindowinMilliseconds", value = "5000"),
//断路器强制打开
@HystrixProperty(name = "circuitBreaker.forceOpen", value = "true"),
//断路器强制关闭
@HystrixProperty(name = "circuitBreaker.forceClosed", value = "true"),
//滚动时间窗设置,该时间用于断路器判断健康度时需要收集信息的持续时间
@HystrixProperty(name = "metrics.rollingStats.timeinMilliseconds", value = "10000"),
//该属性用来设置滚动时间窗统计指标信息时划分"桶"的数量,断路器在收集指标信息的时候会根据设置的时间窗长度拆分成
//多个"桶"来累计各度量值,每个"桶"记录了一段时间内的采集指标。
//比如10秒内拆分成10个"桶"收集指标,所以timeinMilliseconds必须能被numBuckets整除,否则会抛出异常
@HystrixProperty(name = "metrics.rollingStats.numBuckets", value = "10"),
//该属性用来设置对命令执行的延迟是否使用百分位数来跟踪和计算,如果设置为false,那么所有的概要统计都将返回-1
@HystrixProperty(name = "metrics.rollingPercentile.enabled", value = "false"),
//该属性用来设置百分位统计的滚动窗口的持续时间,单位为毫秒
@HystrixProperty(name = "metrics.rollingPercentile.timeInMilliseconds", value = "60000"),
//该属性用来设置百分位统计滚动窗口中使用"桶"的数量
@HystrixProperty(name = "metrics.rollingPercentile。numBuckets", value = "60000"),
//该属性用来设置在执行过程中每个"桶"中保留的最大执行次数。如果在滚动事件窗内发生超过该设定值的执行次数,
//就从最初的位置开始重写。例如,将该值设置为100,滚动窗口为10秒,若在10秒内一个"桶"中发生了500次执行,
//那么该"桶"中只保留最后的100次执行的统计,另外,增加该值的大小将会增加内存量的消耗,并增加排序百分位数所需的计算时间
@HystrixProperty(name = "metrics.rollingPercentile.bucketSize", value = "100"),
//该属性用来设置采集影响断路器状态的健康快照 (请求的成功、错误百分比) 的间隔等待时间
@HystrixProperty(name = "metrics.healthSnapshot.intervalinMilliseconds", value = "500"),
//是否开启请求缓存
@HystrixProperty(name = "requestCache,enabled", value = "true"),
//HystrixCommand的执行和事件是否打印日志到HystrixRequestlog中
@HystrixProperty(name = "requestLog,enabled", value = "true"),
},
threadPoolProperties = {
//该参数用来设置执行命令线程池的核心线程数,该值也就是命令执行的最大并发量
@HystrixProperty(name = "coreSize",value = "10"),
//该参数用来设置线程池的最大队列大小,当设置为-1时,线程池将使用SynchronousQueue实现的队列,
//否则将使用LinkedBlockingQueue实现的队列
@HystrixProperty(name = "maxQueueSize",value = "-1"),
//该参数用来为队列设置拒绝阈值。通过该参数,即使队列没有达到最大值也能拒绝请求,
//该参数主要是对LinkedBlockingQueue队列的补充,因为LinkedBlockingQueue队列
//不能动态修改它的对象大小,而通过该属性就可以调整拒绝请求的队列大小了
@HystrixProperty(name = "queueSizeRejectionThreshold",value = "5"),
}
)
除了隔离依赖服务的调用以外,Hystrix还提供了准实时的调用监控 (Hystrix Dashboard),Hystrix会持续地记录所有通过Hystrix发起的请求的执行信息,并以统计报表和图形的形式展现给用户,包括每秒执行多少请求多少成功,多少失败等。Netflix通过hystrix-metrics-event-stream项目实现了对以上指标的监控。Spring Cloud也提供了Hystrix Dashboard的整合,对监控内容转化成可视化界面。
1、建Module
cloud-consumer-hystrix-dashboard9001
2、改pom
org.springframework.cloud
spring-cloud-starter-netflix-hystrix-dashboard
org.springframework.boot
spring-boot-starter-web
org.springframework.boot
spring-boot-starter-actuator
org.springframework.boot
spring-boot-devtools
runtime
true
org.projectlombok
lombok
true
org.springframework.boot
spring-boot-starter-test
test
3、写yml
server:
port: 9001
4、主启动
@SpringBootApplication
@EnableHystrixDashboard //开启仪表盘功能
public class HystrixDashboardMain9001 {
public static void main(String[] args) {
SpringApplication.run(HystrixDashboardMain9001.class, args);
}
}
5、在需要被监控的服务中添加dashboard配置
8001中
#添加dashboard监控配置
management:
endpoints:
web:
exposure:
include: hystrix.stream
6、测试
输入 http://localhost:9001/hystrix ,进入仪表盘界面
http://localhost:8001/actuator/hystrix.stream
输入8001服务的地址+hystrix路径
hystrix只能监控经过@HystrixCommand注解的方法