微服务是根据业务拆分成一个个的服务,各个服务之间可以相互调用。Spring Cloud可以用RestTemplate+Ribbon和Feign来调用。为了保证其高可用,单个服务通常会集群部署。由于网络原因和自身原因,服务不能保证100%可用,如果单个服务出现问题,调用这个服务的就会出现阻塞,此时如果有大量请求,Servlet容器的线程资源会被消耗完毕,导致服务瘫痪。服务与服务之间的依赖性、故障等会相互传播,会对整个微服务系统造成灾难性的严重后果,这就是服务故障的“雪崩”效应。
Netflix开源了Hystrix组件,实现了断路器模式,SpringCloud对这一组件进行了整合
- 在微服务架构中,一个请求需要调用多个服务是非常常见的。
通过上图可以看出,较低层的服务如果出现故障,会导致连锁故障。当对特定的服务的调用的不可用达到一个阀值(Hystric 是5秒20次)断路器就会被打开。
<dependency>
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-starter-netflix-hystrix</artifactId>
</dependency>
我的服务消费模块的pom文件里添加了断路器依赖包
我的这个项目的启动类添加
测试类修改如下
启动我项目中的服务注册中心
再启动我的服务提供者
此时
我的服务消费者测试接口
所以在网页访问http://localhost:8763/hello?name=zhao
将服务提供者停止
再访问http://localhost:8763/hello?name=zhao
这说明了如果服务提供者不可用时,消费该服务的服务消费者就会执行失败,这就很好的控制了容器的线程阻塞
Hystrix Dashboard(断路器:Hystrix仪表盘)(Feign仪表盘实现跟这个一样)
在上诉consumer这个module里的pom配置文件添加下列依赖包,pom.xml添加依赖
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-actuator</artifactId>
<version>2.0.0.RELEASE</version>
</dependency>
<dependency>
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-starter-hystrix-dashboard</artifactId>
<version>1.4.4.RELEASE</version>
</dependency>
启动类添加
@EnableHystrixDashboard
@EnableCircuitBreaker这两个注解
浏览器访问http://localhost:8763/hystrix
接着
出现的监控界面结果如下
出现这个错误是因为:springboot 版本如果是2.0,则需要添加 ServletRegistrationBean 因为springboot的默认路径不是 "/hystrix.stream"。
解决方法:给ServiceRibbonApplication注入bean
@Bean
public ServletRegistrationBean getServlet() {
HystrixMetricsStreamServlet streamServlet = new HystrixMetricsStreamServlet();
ServletRegistrationBean registrationBean = new ServletRegistrationBean(streamServlet);
registrationBean.setLoadOnStartup(1);
registrationBean.addUrlMappings("/hystrix.stream");
registrationBean.setName("HystrixMetricsStreamServlet");
return registrationBean;
}
此时启动类
package com.hand.customer;
import com.netflix.hystrix.contrib.metrics.eventstream.HystrixMetricsStreamServlet;
import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;
import org.springframework.boot.web.servlet.ServletRegistrationBean;
import org.springframework.cloud.client.circuitbreaker.EnableCircuitBreaker;
import org.springframework.cloud.client.discovery.EnableDiscoveryClient;
import org.springframework.cloud.client.loadbalancer.LoadBalanced;
import org.springframework.cloud.netflix.hystrix.EnableHystrix;
import org.springframework.cloud.netflix.hystrix.dashboard.EnableHystrixDashboard;
import org.springframework.context.annotation.Bean;
import org.springframework.web.client.RestTemplate;
@SpringBootApplication
@EnableDiscoveryClient
@EnableHystrix
@EnableHystrixDashboard
@EnableCircuitBreaker
public class CustomerApplication {
public static void main(String[] args) {
SpringApplication.run(CustomerApplication.class, args);
}
@Bean
@LoadBalanced
RestTemplate restTemplate(){
return new RestTemplate();
}
@Bean
public ServletRegistrationBean getServlet() {
HystrixMetricsStreamServlet streamServlet = new HystrixMetricsStreamServlet();
ServletRegistrationBean registrationBean = new ServletRegistrationBean(streamServlet);
registrationBean.setLoadOnStartup(1);
registrationBean.addUrlMappings("/hystrix.stream");
registrationBean.setName("HystrixMetricsStreamServlet");
return registrationBean;
}
}
重新启动CustomerApplication
刷新监控页面结果如下
其他页面访问http://localhost:8763/hello?name=meng,再看监控页面如下,说明有数据响应
SpringCloud服务发现组件Eureka常见问题汇总 https://blog.csdn.net/qq_15898739/article/details/90022035
源代码