SpringCloud断路器Hystrix原理及用法解析
作者:1994的地铁 发布时间:2022-03-20 16:47:41
这篇文章主要介绍了SpringCloud断路器Hystrix原理及用法解析,文中通过示例代码介绍的非常详细,对大家的学习或者工作具有一定的参考学习价值,需要的朋友可以参考下
在分布式环境中,许多服务依赖项中的一些必然会失败。Hystrix是一个库,通过添加延迟容忍和容错逻辑,帮助你控制这些分布式服务之间的交互。Hystrix通过隔离服务之间的访问点、停止级联失败和提供回退选项来实现这一点,所有这些都可以提高系统的整体弹性
两个比较重要的类
HystrixCommand
HystrixObservableCommand
注解@HystrixCommand(fallbackMethods="methods")methods中可以添加降级策略
除了提供服务降级
还提供了请求缓存
@CacheResult
@CacheRemve
不过添加CacheResult的时候,说
HystrixRequestContext未初始化。
2020-01-13 16:12:10.273 ERROR 15348 --- [nio-8083-exec-1] o.a.c.c.C.[.[.[/].[dispatcherServlet] : Servlet.service() for servlet [dispatcherServlet] in context with path [] threw exception [Request processing failed; nested exception is java.lang.reflect.UndeclaredThrowableException] with root cause
java.lang.IllegalStateException: Request caching is not available. Maybe you need to initialize the HystrixRequestContext?
at com.netflix.hystrix.HystrixRequestCache.get(HystrixRequestCache.java:104) ~[hystrix-core-1.5.18.jar:1.5.18]
at com.netflix.hystrix.AbstractCommand$7.call(AbstractCommand.java:478) ~[hystrix-core-1.5.18.jar:1.5.18]
at com.netflix.hystrix.AbstractCommand$7.call(AbstractCommand.java:454) ~[hystrix-core-1.5.18.jar:1.5.18]
at rx.internal.operators.OnSubscribeDefer.call(OnSubscribeDefer.java:46) ~[rxjava-1.3.8.jar:1.3.8]
at rx.internal.operators.OnSubscribeDefer.call(OnSubscribeDefer.java:35) ~[rxjava-1.3.8.jar:1.3.8]
查看官方文档https://github.com/Netflix/Hystrix/wiki/How-To-Use
Typically this context will be initialized and shut down via a ServletFilter that wraps a user request or some other lifecycle hook.
在同一用户请求的上下文中,相同依赖服务的返回数据始终保持一致。在当次请求内对同一个依赖进行重复调用,只会真实调用一次。在当次请求内数据可以保证一致性。
初始化是在filter中进行(官方建议),但是每一次请求都会进行初始化 。所以说和一般的缓存还是有去别的,可以解决高并发,保证的资源的线程安全。在某些场景很有用。
请求合并
/**
* 建议: 服务提供方有较高的延迟。可以考虑使用请求合并
* HystrixCollapser 合并请求的时候会创建一个请求处理器。如果每次合并的请求量不大,只有很少的请求还要合并,会造成合并时间窗
* 并发量增大,时间窗的创建和消耗增大。所以只有在时间窗内有很大的并发量,推荐请求合并。
*
* batchMethod 请求合并后的替换方法com.gitee.munan56.cloud.hystrixconsumer.AService#findALl(java.util.List) 注意客户端要有这个方法
*HystrixProperty 一个属性合并时间窗100s 这个时间结束后会发起请求,也就是指这个时间是合并处理的时间
* @param id
* @return
*/
@HystrixCollapser(batchMethod = "findALl",collapserProperties = @HystrixProperty(name = "timerDelayInMilliseconds",value = "100"))
public String doBFindOne(String id){
System.out.println("begin do provider service");
return restTemplate.getForEntity("http://service-provider:8081/api/v1/provider/do",String.class).getBody();
}
全部代码
package com.gitee.munan56.cloud.hystrixconsumer;
import com.netflix.hystrix.contrib.javanica.annotation.HystrixCollapser;
import com.netflix.hystrix.contrib.javanica.annotation.HystrixCommand;
import com.netflix.hystrix.contrib.javanica.annotation.HystrixProperty;
import com.netflix.hystrix.contrib.javanica.cache.annotation.CacheResult;
import com.netflix.hystrix.strategy.concurrency.HystrixRequestContext;
import com.netflix.ribbon.proxy.annotation.Hystrix;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.springframework.web.client.RestTemplate;
import java.util.List;
/**
* @author munan
* @version 1.0
* @date 2020/1/13 10:41
*/
@Service
public class AService {
@Autowired
private RestTemplate restTemplate;
public String doAService(){
return "A Service is run";
}
// @Hystrix(fallbackHandler = )
@HystrixCommand(fallbackMethod = "error")
public String doBServiceOne(){
System.out.println("begin do provider service");
return restTemplate.getForEntity("http://service-provider:8081/api/v1/provider/do",String.class).getBody();
}
/**
* CacheResult 请求缓存(针对request的缓存),官方建议在serverlet filter 中初始化HystrixRequestContext
* 在同一用户请求的上下文中缓存在统一请求的上下文环境中有效。
* @param id
* @return
*/
@CacheResult(cacheKeyMethod = "getKey")
@HystrixCommand(fallbackMethod = "error")
public String doBServiceTwo(String id){
System.out.println("begin do provider service");
return restTemplate.getForEntity("http://service-provider:8081/api/v1/provider/do",String.class).getBody();
}
/**
* 建议: 服务提供方有较高的延迟。可以考虑使用请求合并
* HystrixCollapser 合并请求的时候会创建一个请求处理器。如果每次合并的请求量不大,只有很少的请求还要合并,会造成合并时间窗
* 并发量增大,时间窗的创建和消耗增大。所以只有在时间窗内有很大的并发量,推荐请求合并。
*
* batchMethod 请求合并后的替换方法com.gitee.munan56.cloud.hystrixconsumer.AService#findALl(java.util.List) 注意客户端要有这个方法
*HystrixProperty 一个属性合并时间窗100s 这个时间结束后会发起请求,也就是指这个时间是合并处理的时间
* @param id
* @return
*/
@HystrixCollapser(batchMethod = "findALl",collapserProperties = @HystrixProperty(name = "timerDelayInMilliseconds",value = "100"))
public String doBFindOne(String id){
System.out.println("begin do provider service");
return restTemplate.getForEntity("http://service-provider:8081/api/v1/provider/do",String.class).getBody();
}
@HystrixCommand()
public String findALl(List<String> ids){
System.out.println("begin do provider service");
return restTemplate.getForEntity("http://service-provider:8081/api/v1/provider/do",String.class).getBody();
}
/**
* 服务降级
* 指定调用服务出错的回调方法
* @return
*/
public String error(Throwable e){
return "do provider error this is default result" + "the error is " + e.getMessage();
}
/**
* 服务降级
* 指定调用服务出错的回调方法
* @return
*/
public String error(String id ,Throwable e){
return "do provider error this is default result" + "the error is " + e.getMessage();
}
public String getKey(String id){
return id;
}
}
来源:https://www.cnblogs.com/munan56/p/12188935.html
猜你喜欢
- Controller如何进行重定向Spring MVC中进行重定向本人知道的有两种方式方法返回的URI(相对路径)中加上"redi
- SpringBoot配置文件中设置server.port不生效我的配置文件为:# application.ymlserver:
- 介绍该系统有三个角色,分别是:普通用户、房屋中介、管理员。普通用户的功能:浏览房屋信息、预约看房、和中介聊天、申请成为中介等等。房屋中介的功
- Java Config 下的Spring Test方式用了三种方式:1.纯手动取bean:package com.wang.test;imp
- 前言:学习了SpringBoot分页查询的两种写法,一种是手动实现,另一种是使用框架实现。现在我将具体的实现流程分享一下。首先是手动实现分页
- 本篇紧接上一篇内容继续,还是从继承里的细节开始1.代码块初始化关于代码块的定义和使用因为之前已经进行过介绍,所以这里就不再赘述,我们所关注的
- 本文实例讲述了java识别一篇文章中某单词出现个数的方法。分享给大家供大家参考。具体如下:1. java代码:import java.io.
- RabbitMQ作为AMQP的代表性产品,在项目中大量使用。结合现在主流的spring boot,极大简化了开发过程中所涉及到的消息通信问题
- 它可以做什么?它做的事情当然是生成新类或修改原始的类,比如你遇到这样的情况下就可以使用:反射好慢,曾见过一个大厂大量是Gson,由于Gson
- 本文实例为大家分享了Java实现简单ATM机功能的具体代码,供大家参考,具体内容如下项目介绍基于大家使用银行卡在ATM机取款操作,进行相对应
- 概述:Spring Boot 2.0相对于之前的版本,变化还是很大的。首先对jdk的版本要求已经不能低于1.8,其次依赖的spring的版本
- 前言本文主要给大家介绍的是java虚拟机的故障处理工具,文中提到这些工具包括:名称主要作用jpsJVM process Status Too
- 本文实例讲述了C#串口通信实现方法。分享给大家供大家参考。具体方法如下:通过COM1发送数据,COM2接收数据。当COM2接收完本次发送的数
- Spring提供的工具类,主要用于框架内部使用,这个类提供了一些简单的方法,并且提供了易于使用的方法在分割字符串,如CSV字符串,以及集合和
- 本文实例讲述了C#设置页面单位和缩放的方法。分享给大家供大家参考。具体如下:using System;using System.Collec
- 策略模式的应用场景策略模式是否要使用,取决于业务场景是否符合,有没有必要。是否符合如果业务是处于不同的场景时,采取不同的处理方式的话,就满足
- @Autowired使用构造函数注入public Class Outer { private Inner inner; @Autowired
- 最近没做项目,重新整理了一个最完整的Mybatis Generator(简称MBG)的最完整配置文件,带详解,再也不用去看EN的User G
- 本文实例为大家分享了Java实现双向链表的具体代码,供大家参考,具体内容如下双向链表与单链表的对比:1、单向链表查找只能是一个方向,双向链表
- 需求:用户和账户一对一关系,查询账户时实现用户的延迟加载思路:根据id查询,需要延迟加载的一方1、用户实体类package com.yl.b