通过前3节的SpringCloud学习,理解了服务的提供者可能不止有一个端口,在当前的真正的工作中可能还不止有一个微服务来提供服务。如果服务崩掉,如果没有措施,会导致很重大的损失。
就比方如果提供的是购物服务,总不可能让顾客买货色。还有生存中最常见的例子是当家庭某个电器短路的时候,为了保障整体电器,保险丝就会进行熔断。
Hystrix的诞生就是为了解决这个问题。
1 引入Hystrix
建设hystrix
父模块,批改父模块pom文件使其子模块都导入了依赖,不便当前操作。
<dependencies> <dependency> <groupId>org.springframework.cloud</groupId> <artifactId>spring-cloud-starter-netflix-hystrix</artifactId> </dependency></dependencies>
随后在父模块下新建一个hystrix-consume9301
子模块,最初的我的项目构造目录如下:
2 主启动类和配置文件
配置文件:
spring: application: name: hystrix-consume9301server: port: 9301eureka: client: fetch-registry: true register-with-eureka: true service-url: defaultZone: http://localhost:8001/eureka/ instance: instance-id: hystrix-consume9301
其实配置文件简略来说都是一样的,始终反复写进去就是为了大家不便cv复现
主启动类:
@SpringBootApplication@EnableEurekaClient@EnableHystrix //开启Hystrix@RestController //开启业务类public class HystrixConsume9301 { public static void main(String[] args) { SpringApplication.run(HystrixConsume9301.class, args); }}
3 业务类
再次强调是为了不便入门,间接在主启动类中编写业务类,这是不标准的。
为了可能进行服务间的调用,在入门Eureka的时候也说到了利用RestTemplate
即可,所以须要增加一个config类把RestTemplate
注入到Spring容器中。
@Configurationpublic class ApplicationContextConfig { @Bean @LoadBalanced //开启负载平衡性能,加了此注解能力通过服务名来拜访服务 public RestTemplate getRestTemplate() { return new RestTemplate(); }}
回过来看主启动类
@SpringBootApplication@EnableEurekaClient@EnableHystrix //开启Hystrix@RestController //开启业务类public class HystrixConsume9301 { public static void main(String[] args) { SpringApplication.run(HystrixConsume9301.class, args); } //服务名字 final String PROVIDE_URL = "http://eureka-provide"; RestTemplate restTemplate; public HystrixConsume9301(RestTemplate restTemplate) { this.restTemplate = restTemplate; } @GetMapping("/hystrix/consume") @HystrixCommand(fallbackMethod = "getInfoFallback") //开启降级服务 public String getInfo() { return "i am hystrix consumer, but actually invoke provide service: [" + restTemplate.getForObject(PROVIDE_URL + "/eureka/provide", String.class) + "]"; } public String getInfoFallback() { return "hello, something wrong, i am getInfo fallback method"; }}
其它所有都一样,只不过是在相应的业务办法中增加了@HystrixCommand
注解,该注解中的fallbackMethod
申明的是服务降级后回调的是哪个办法。
4 测试
开启Eureka服务注册核心EurekaServer8001
,服务提供者EurekaProvide7001
,[7002, 7003],开启HystrixConsume9301
拜访http://localhost:9301/hystrix...
然而当咱们把所有的服务提供者EurekaProvide7001
停掉以模仿服务挂掉的状况,测试后果如图所示。能够看到服务并没有报错,的确降级调用咱们想要调用的办法。
5 扩大
对于扩大方面,这里就略微提下@HystrixProperty
注解,间接看例子。
通过sleep()
函数来模仿服务提供端提早提供服务
首先须要批改的是服务提供端的代码,服务提供端的代码,服务提供端的代码 。也就是本系列第一篇文章中的eureka-client-provide7001子模块我的项目
@SpringBootApplication@RestController@EnableEurekaClientpublic class EurekaProvide7001 { @Value("${server.port}") int port; @GetMapping("/eureka/provide") public String getInfo() { return "hello, i am eureka provide, the provide service. My port: " + port; } //上面是增加的内容 @GetMapping("/eureka/delayProvide") public String delayGetInfo() throws InterruptedException { Thread.sleep(3000); //提早3秒才执行真正的业务逻辑 return "hello, delay to do something"; } public static void main(String[] args) { SpringApplication.run(EurekaProvide7001.class, args); }}
而后批改Hystrix生产端的代码
@SpringBootApplication@EnableEurekaClient@EnableHystrix@RestControllerpublic class HystrixConsume9301 { public static void main(String[] args) { SpringApplication.run(HystrixConsume9301.class, args); } final String PROVIDE_URL = "http://eureka-provide"; RestTemplate restTemplate; public HystrixConsume9301(RestTemplate restTemplate) { this.restTemplate = restTemplate; } //省略一部分 @HystrixCommand(commandProperties = { @HystrixProperty(name = "execution.isolation.thread.timeoutInMilliseconds", value = "5000") }, fallbackMethod = "getPropFallback") @GetMapping("hystrix/normalConsume") public String getNormalConsumeInfo() { long start = System.currentTimeMillis(); String res = restTemplate.getForObject(PROVIDE_URL + "/eureka/delayProvide", String.class); long end = System.currentTimeMillis(); res += "[cost time: " + (end - start) + "]"; return res; } @HystrixCommand(commandProperties = { @HystrixProperty(name = "execution.isolation.thread.timeoutInMilliseconds", value = "2000") }, fallbackMethod = "getPropFallback") @GetMapping("hystrix/timeoutConsume") public String getTimeoutConsumeInfo() { long start = System.currentTimeMillis(); String res = restTemplate.getForObject(PROVIDE_URL + "/eureka/delayProvide", String.class); long end = System.currentTimeMillis(); res += "[cost time: " + (end - start) + "]"; return res; } public String getPropFallback() { return "timeout, fallback method, do something."; }}
@HystrixProperty(name = "execution.isolation.thread.timeoutInMilliseconds", value = "5000"
次要示意的是在规定的工夫(5000)如果能调用服务,那么就不fallback。
下面的服务是提早了3000ms执行业务,而后我设置了一个回调阈值是5000ms,一个是2000ms。
开始测试前留神把方才停掉的服务提供者EurekaProvide7001
开启 ,模仿的是提早调用服务,并不是服务挂掉了。首先拜访http://localhost:9301/hystrix...
能够看到转圈圈是大略3s后有响应,同时通过耗费的工夫也能够看出。
那么当拜访超时接口后http://localhost:9301/hystrix...
能够看到转圈圈是大略2s后有响应,并且调用的是fallback办法,并不是服务提供办法。上种状况转3s是因为服务调用是3s,这种状况转2s是因为咱们设置了回调阈值是2s,到2s后还没调用服务就调用fallback。
6 Hystrix Dashboard
这是一款可视化的监控,次要是帮忙咱们直观地看到了Hystrix Command无关响应的一些指标
引入依赖
批改hystrix-consume
9301子模块下的pom文件 ,往其中增加依赖
<dependencies> <dependency> <groupId>org.springframework.cloud</groupId> <artifactId>spring-cloud-starter-netflix-hystrix-dashboard</artifactId> </dependency></dependencies>
批改主启动类,减少Bean
@SpringBootApplication@EnableEurekaClient@EnableHystrixDashboard //开启可视化界面,其实就是多加了这个注解@EnableHystrix@RestControllerpublic class HystrixConsume9301 { }
此时能够启动主启动类来拜访http://localhost:9301/hystrix
看到这个界面阐明配置胜利,值得注意的是咱们还须要减少一个Bean的配置类才可能正确运行,在config包下新建一个类ServletRegisterBeanConfig
@Configurationpublic class ServletRegisterBeanConfig { @Bean(name = "registerBean") public ServletRegistrationBean getServlet(){ HystrixMetricsStreamServlet streamServlet = new HystrixMetricsStreamServlet(); ServletRegistrationBean registrationBean = new ServletRegistrationBean(streamServlet); registrationBean.setLoadOnStartup(1); registrationBean.addUrlMappings("/actuator/hystrix.stream"); registrationBean.setName("HystrixMetricsStreamServlet"); return registrationBean; }}
最初重新启动HystrixConsume9301
主启动类,再次拜访http://localhost:9301/hystrix...
当点击监控流后,会发现dashboard界面和控制台同时报错
批改配置文件
依照控制台报错批改管制文件,退出
hystrix: dashboard: proxy-stream-allow-list: localhost
重启我的项目,此时反复上述操作能够看到正确运行,期待连贯
测试
开启Eureka服务注册核心EurekaServer8001
,服务提供者EurekaProvide7001
,[7002, 7003],开启HystrixConsume9301
。拜访生产接口http://localhost:9301/hystrix... ,http://localhost:9301/hystrix... ,http://localhost:9301/hystrix...
能够看到的确可能实时监控到申请,并且有对应的指标。
创作不易,如果对你有帮忙,欢送点赞,珍藏和分享啦!
上面是集体公众号,有趣味的能够关注一下,说不定就是你的宝藏公众号哦,根本2,3天1更技术文章!!!