熔断机制:


是应对雪崩效应的一种微服务链路保护机制。
当某个微服务不可用或者响应时间太长时,会进行服务降级,进而熔断该节点微服务的调用,快速返回“错误”的响应信息。当检测到该节点微服务调用响应正常后恢复调用链路。
在SpringCloud框架里熔断机制通过Hystrix实现,Hystrix会监控微服务间调用的状况,当失败的调用到一定阈值,缺省是5秒内调用20次,如果失败,就会启动熔断机制。

服务降级:


一般是从整体负荷考虑。就是当某个服务熔断之后,服务器将不再被调用,此时客户端可以自己准备一个本地的fallback回调,返回一个缺省值

服务熔断

熔断机制是服务雪崩的一种有效解决方案。当指定时间窗内的请求失败率达到设定阈值时,系统将通过断路器直接将此请求链路断开。常见的熔断有两种:
预熔断
即时熔断

什么是服务熔断:


熔断机制是应对雪崩效应的一种微服务链路保护机制.
服务熔断的作用类似于我们家用的保险丝,当某服务出现不可用或响应超时的情况时,为了防止整个系统出现雪崩,暂时停止对该服务的调用。服务熔断是在生产者(product)配置的.

当扇出链路的某个微服务不可用或者响应时间太长时,会进行服务的降级,进而熔断该节点微服务的调用,快速返回”错误”的响应信息,当检测到该节点微服务调用响应正常后恢复调用链路,在SpringCloud框架里熔断机制通过Hystrix实现,Hystrix会监控微服务间调用的状态,当失败的调用到一定阈值,缺省是5秒内20次调用失败就会启用熔断机制,熔断机制的注解是@HystrixCommand.

当服务的生产者出现异常Exception异常的时候,就会触发服务熔断,@HystrixCommand的fallbackMethod配置熔断方法,也可以指定多少秒没有返回结果就算调用失败,执行fallbackMethod指定的方法.


其实这种情况类似于异常捕获机制,当出现异常,返回一个通用的接口报文

【microcloud-provider-product】 复制一份成为【microcloud-provider-product-hystrix】

【microcloud-provider-product-hystrix】修改pom文件,增加 Hystrix依赖

org.springframework.cloud
spring-cloud-starter-netflix-hystrix


【microcloud-provider-product-hystrix】 修改ProductController
package cn.enjoy.controller;

import cn.enjoy.service.IProductService;
import cn.enjoy.vo.Product;
import com.netflix.hystrix.contrib.javanica.annotation.HystrixCommand;
import org.springframework.cloud.client.discovery.DiscoveryClient;
import org.springframework.web.bind.annotation.*;
import javax.annotation.Resource;

@RestController
@RequestMapping(“/prodcut”)
public class ProductController {

@Resource
private IProductService iProductService;

@Resource
private DiscoveryClient client ; // 进行Eureka的发现服务

@RequestMapping(value=”/get/{id}”)
@HystrixCommand(fallbackMethod = “getFallback”)
public Object get(@PathVariable(“id”) long id) {
Product product = this.iProductService.get(id);
if(product == null) {
throw new RuntimeException(“该产品已下架!”) ;
}
return product;
}

public Object getFallback(@PathVariable(“id”) long id){
Product product = new Product();
product.setProductName(“HystrixName”);
product.setProductDesc(“HystrixDesc”);
product.setProductId(0L);
return product;
}


@RequestMapping(value=”/add”)
public Object add(@RequestBody Product product) {
return this.iProductService.add(product) ;
}
@RequestMapping(value=”/list”)
public Object list() {
return this.iProductService.list() ;
}


@RequestMapping(“/discover”)
public Object discover() { // 直接返回发现服务信息
return this.client ;
}
}


一旦 get()方法上抛出了错误的信息,那么就认为该服务有问题
会默认使用“@HystrixCommand”注解之中配置好的fallbackMethod 调用类中的指定方法,返回相应数据

【microcloud-provider-product-hystrix】修改启动类,增加对熔断的支持
package cn.enjoy;

import org.mybatis.spring.annotation.MapperScan;
import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;
import org.springframework.cloud.client.circuitbreaker.EnableCircuitBreaker;
import org.springframework.cloud.client.discovery.EnableDiscoveryClient;
import org.springframework.cloud.netflix.eureka.EnableEurekaClient;

@SpringBootApplication
@MapperScan(“cn.enjoy.mapper”)
@EnableEurekaClient
@EnableDiscoveryClient
@EnableCircuitBreaker
public class ProductHystrixApp {
public static void main(String[] args) {
SpringApplication.run(ProductHystrixApp.class,args);
}
}


测试: localhost//consumer/product/get?id=1 get请求

1.设置超时自动服务熔断

在上面的基础上在生产者需要设置超时自动进行服务熔断的方法上使用@HystrixProperty注解即可
参考: https://www.cnblogs.com/yjmyzz/p/spring-cloud-hystrix-tutorial.html

@RequestMapping(value = “/get/{id}”)
//如果程序出现异常,会直接调用fallbackMethod 指定的方法 @HystrixCommand(fallbackMethod = “getFallback”, commandProperties =
//如果一秒内没有返回结果,就算调用失败,执行fallbackMethod指定的方法 {@HystrixProperty(name = “execution.isolation.thread.timeoutInMilliseconds”, value = “1000”)
})
public Object get(@PathVariable(“id”) long id) throws InterruptedException {
//随机睡眠 Thread.sleep(new Random(System.currentTimeMillis()).nextInt(2000));

Product product = this.iProductService.get(id);
if (product == null) {
throw new RuntimeException(“该产品已下架!”);
}
return product;
}

服务降级

服务降级是在服务的消费者那里配置的.假如服务的生产者挂掉了,或者停机了(Eureka显示不到这个服务的Application名字了),此时服务的消费者会直接返回实现FallbackFactory接口的重新执行方法的代码块儿,可以在这里写一些业务逻辑,比如记录日志啥的,或者是返回友好的东西给用户等等.


在某些情况下,服务提供方并没有失效,但可能由于网络原因,服务的消费方并不能调用到服务接口,在这种情况下,直接在服务的提供方提供熔断机制依然还是不够的,这方面的处理需要在服务的消费方进行服务的回退处理

服务降级指的是当服务的提供方(product,生产者)不可使用的时候,程序不会出现异常,而会出现本地的操作调用,服务的降级是在服务消费方(consumer)实现的,在断网情况下服务提供方的任何处理都是没有意义的。

服务降级是在客户端实现完成的,与服务端没有关系,服务降级就是如客户端在服务端不可用的时候,也会获得提示信息而不会挂起引起耗死服务器.


【microcloud-service】新增一个IProductClientService的失败调用(降级处理)

package cn.enjoy.service.fallback;


import cn.enjoy.service.IProductClientService;
import cn.enjoy.vo.Product;
import feign.hystrix.FallbackFactory;
import org.springframework.stereotype.Component;

import java.util.List;

@Component
public class IProductClientServiceFallbackFactory implements FallbackFactory {
@Override
public IProductClientService create(Throwable throwable) {
return new IProductClientService() {
@Override
public Product getProduct(long id) {
Product product = new Product();
product.setProductId(999999L);
product.setProductName(“feign-hystrixName”);
product.setProductDesc(“feign-hystrixDesc”);
return product;
}

@Override
public List listProduct() {
return null;
}

@Override
public boolean addPorduct(Product product) {
return false;
}
};
}
}


【microcloud-service】 修改IProductClientService,增加fallback配置
package cn.enjoy.service;


import cn.enjoy.feign.FeignClientConfig;
import cn.enjoy.service.fallback.IProductClientServiceFallbackFactory;
import cn.enjoy.vo.Product;
import org.springframework.cloud.openfeign.FeignClient;
import org.springframework.web.bind.annotation.PathVariable;
import org.springframework.web.bind.annotation.RequestMapping;

import java.util.List;

@FeignClient(name = “MICROCLOUD-PROVIDER-PRODUCT”,configuration = FeignClientConfig.class,
fallbackFactory = IProductClientServiceFallbackFactory.class)
public interface IProductClientService {
@RequestMapping(“/prodcut/get/{id}”)
public Product getProduct(@PathVariable(“id”)long id);

@RequestMapping(“/prodcut/list”)
public List listProduct() ;

@RequestMapping(“/prodcut/add”)
public boolean addPorduct(Product product) ;

}



【microcloud-consumer-feign】 复制一份成为【microcloud-consumer-hystrix】模块
注意!!! 直接复制会报错,建议直接在原来的 【microcloud-consumer-feign】 项目修改,报错是下面的错误:
https://blog.csdn.net/qq_38340677/article/details/89222029 意思是@FeignClient的定义的名字下面有多个实现的消费者


【microcloud-consumer-hystrix】 修改application.yml配置文件,启用hystrix配置
feign:
hystrix:
enabled: true
compression:
request:
enabled: true
mime-types: # 可以被压缩的类型
- text/xml
- application/xml
- application/json
min-request-size: 2048 # 超过2048的字节进行压缩

启动,服务提供者 启动项目 Eureka 和microcloud-provider-product-hystrix 和microcloud-consumer-feign-hystrix项目测试

访问:http://localhost/consumer/product/get?id=2,能正常访问
关闭,服务提供者(microcloud-provider-product-hystrix)
访问:http://localhost/consumer/product/get?id=2,也能正常访问

服务熔断和服务降级的区别


服务熔断:

一般是某个服务故障或者异常引起的,类似现实世界中的”保险丝”,当某个异常条件被触发,直接熔断整个服务,而不是一直等到此服务超时. 服务熔断是在服务的生产者那里设置


服务降级:

所谓降级,一般是从整体负荷考虑,就是当某个服务熔断之后,服务器将不再被调用,此时客户端可以自己准备一个本地的fallback回调,返回一个缺省值,这样做,虽然服务水平下降,但是好歹可以使用,比直接挂掉要强.

服务降级是在服务的消费者和接口的提供者那里设置 (microcloud-service和microcloud-consumer-feign-hystrix)

服务熔断是在服务端提供者product那里配置.