Spring Cloud中怎么使用Resilience4j Retry对OpenFeign进行重试

news2025/1/9 16:45:03

在微服务架构中,服务之间的通信是非常频繁的。而使用OpenFeign可以极大简化微服务之间的HTTP通信。但在复杂的分布式系统中,服务之间的调用可能会因为网络问题、服务故障等原因而失败。因此,实现服务调用的重试机制显得尤为重要。Resilience4j是一个功能强大的库,它提供了多种容错机制,包括重试(Retry)、熔断(CircuitBreaker)、限流(RateLimiter)等。本篇文章将详细介绍如何在Spring Cloud中使用Resilience4j Retry对OpenFeign进行重试。

一、Resilience4j Retry原理 

Resilience4j的Retry模块允许在调用失败时进行自动重试。它支持以下几种特性:

  • 自定义重试次数:可以配置最大重试次数。
  • 自定义等待时间:可以配置每次重试之间的等待时间。
  • 重试条件:可以配置哪些异常类型触发重试。

Resilience4j Retry的工作流程如下:

  1. 方法调用:对目标方法进行调用。
  2. 异常捕获:如果目标方法抛出配置的异常,则捕获该异常。
  3. 重试判断:判断是否满足重试条件以及重试次数是否已达到上限。
  4. 重试等待:如果满足重试条件且重试次数未达到上限,则等待配置的时间后再次尝试调用。
  5. 降级处理:如果重试次数达到上限,依然无法成功调用,则执行降级处理逻辑。

 二、项目准备

首先,确保你的Spring Cloud项目中已经引入了必要的依赖,包括Spring Cloud OpenFeign和Resilience4j。

1. 引入依赖

pom.xml中添加以下依赖:

<!--resilience4j-->
<dependency>
    <groupId>org.springframework.cloud</groupId>
    <artifactId>spring-cloud-starter-circuitbreaker-resilience4j</artifactId>
</dependency>
<!-- 由于resilience4j需要AOP的包,所以必须导入AOP包 -->
<dependency>
    <groupId>org.springframework.boot</groupId>
    <artifactId>spring-boot-starter-aop</artifactId>
</dependency>
<dependency>
	<groupId>org.springframework.cloud</groupId>
	<artifactId>spring-cloud-starter-openfeign</artifactId>
</dependency>
2. 启用Feign Clients

确保你的Spring Boot应用程序主类上或者配置类上有@EnableFeignClients注解:

@Configuration
@EnableFeignClients(basePackages = "com.springcloud.sample.service")
@Import(FeignClientsConfiguration.class)
public class FeignConfiguration {

    /**
     * Set the Feign specific log level to log client REST requests.
     */
    @Bean
    feign.Logger.Level feignLoggerLevel() {
        return feign.Logger.Level.BASIC;
    }
}

三、配置Resilience4j Retry 

在你的application.ymlapplication.properties文件中配置Resilience4j的Retry策略。例如:

resilience4j.retry:
  configs:
    default:
      maxRetryAttempts: 3
      waitDuration: 2s
      retryExceptions:
        - org.springframework.web.client.HttpServerErrorException
        - java.io.IOException
        - feign.FeignException

解释:

  • maxRetryAttempts: 最大重试次数,这里设置为3次。
  • waitDuration: 每次重试之间的等待时间,这里设置为2秒。
  • retryExceptions: 配置哪些异常类型触发重试,这里包括HttpServerErrorExceptionIOException和FeignException

四、创建Feign客户端接口

创建一个Feign客户端接口来定义服务间的调用。例如:

@FeignClient("pay-service")
public interface PayService {

    @GetMapping("/pay/{id}")
    String payOrder(@PathVariable("id") Integer id);

}

五、使用Retry注解

在调用Feign客户端的方法上添加@Retry注解,并创建一个fallback方法,用于定义服务调用失败后的降级处理逻辑。例如:

@RestController
public class OrderController {

    private static final Logger log = LoggerFactory.getLogger(OrderController.class);

    @Autowired
    private PayService payService;

    @GetMapping("/order/{id}")
    @Retry(name = "paymentService", fallbackMethod = "fallback")
    public String order(@PathVariable("id") Integer id){
        log.info("Request Pay For Order id: {}", id);
        //通过open feign远程调用支付服务
        return payService.payOrder(id);
    }

    //fallback就是服务降级后的兜底处理方法
    public String fallback(Integer id,Throwable t) {
        log.info("Pay Service invoke failed for order ID: {}", id);
        log.error("Error: {}", t.getMessage());
        return "Pay Service Was Busy Now. Please try again later!";
    }
}

通过上述步骤,当payOrder方法调用失败时,Resilience4j的Retry机制将自动进行重试。如果重试次数超过配置的最大重试次数,Fallback类中的降级逻辑将会被执行。

六、测试

我我们通过关闭目标服务(pay-service)来测试重试机制是否正常工作。在目标服务不可用的情况下,请求/order/1接口,应该会看到系统进行多次重试,然后返回降级信息。

1. 在浏览器中访问order接口

http://localhost:8082/order/1

在访问以上地址后,浏览器并没有立刻返回结果,应该正在进行重试。因为我们已经关闭了目标服务,在等待几秒之后,浏览器返回了降级后的结果。如下:

2. 在控制台中验证是否重试过 

从上面的log中我们可以看出,一共请求了3次,和我们配置的maxRetryAttempts:3 一致,每次请求间隔2s,是我们在配置文件中指定的。并且,在最后一次重试任然失败后,走到了降级的方法 fallback中去,返回默认的降级结果。和我们预期的一样,retry能够正常工作。并且在retryExceptions中我们可以选择下游返回哪些异常时进行重试,我们在进行业务逻辑处理时可以灵活应用。

七、总结

通过上述配置和代码示例,我们在Spring Cloud项目中成功集成了Resilience4j的Retry机制,为OpenFeign的服务调用提供了自动重试功能。Resilience4j提供的灵活配置使得我们可以根据实际需求,精细控制重试策略,从而提高系统的可靠性和稳定性。

希望这篇文章能帮助你更好地理解和使用Resilience4j Retry对OpenFeign进行重试。如果你有任何问题或建议,欢迎在评论区留言交流。

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/1969375.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

DDR3的使用(四)利用XILINX MIGIP核(native)读写DDR3—IP核信号分析

我们这一节继续结合仿真波形和逻辑分析仪测试波形来分析下MIGIP核的各个信号使用&#xff0c;这里主要说的是用户端的信号&#xff0c;这些信号直接与ip核进行交互&#xff0c;只有正确使用才能按我们的要求来读写数据。 1.我们先打开modelsim仿真软件&#xff0c;查看下examp…

机器学习笔记 - RAFT 光流简读

一、光流 光流是图像序列中像素的表观运动。为了估计光流,场景中物体的移动必须具有相应的亮度位移。这意味着一个图像中移动的红球在下一个图像中应该具有相同的亮度和颜色,这使我们能够确定它以像素为单位移动了多少。下图显示了光流示例,其中一系列图像捕获了逆时针旋转的…

使用 宝塔面板 部署 语料库php网站

【语料库网站】宝塔面板 在线部署全过程 代码仓库&#xff1a;https://github.com/talmudmaster/RedCorpus 网站介绍 语料库提供双语文本检索和分享功能。供英语、翻译相关专业的爱好者&#xff0c;学生和老师学习使用。 该网站是对BiCorpus开源项目的二次开发。 技术栈&am…

一文全面了解高性能计算平台是什么、怎么选型?高性能计算平台CHPC 都能做什么?

一. 概述 随着技术的发展和数据量的爆炸性增长&#xff0c;企业面临的挑战日益复杂&#xff0c;对计算能力的需求也在不断增加。这些问题的解决超出了传统计算方法的能力范围&#xff0c;高性能计算&#xff08;HPC&#xff09;正是为解决这类问题而生。 高性能计算&#xff…

怎么锁定Word文档格式,保护文档完整性

在日常工作和学习中&#xff0c;我们经常会使用Word文档来编辑和保存重要信息。然而&#xff0c;在文档被多人编辑或分享的过程中&#xff0c;格式的意外变动往往会给后续工作带来不必要的麻烦。为了确保文档的格式在编辑和分享过程中保持不变&#xff0c;我们可以采取一些措施…

2024还有跨境玩家没解锁代理IP+设备多开模式的强大吗?

大多数跨境电商平台对于IP地址、浏览器环境等限制严格。若同一台电脑在同一个跨境电商平台注册多个账号&#xff0c;很容易被官方封禁。如何在不触发官方封禁机制的前提下&#xff0c;安全高效地开展多账号运营策略&#xff0c;成为了众多跨境电商从业者亟待解决的问题。本文将…

jenkins集成jmeter

jenkins 安装插件HTML Publisher startup trigger Groovy 脚本介绍 cd /app/jmeter rm -rf result.jtl jmeter.log report mkdir -p report sh /app/jmeter/apache-jmeter-5.6.3/bin/jmeter.sh -n -t test.jmx -l result.jtl -e -o ./report-n: 表示以非 GUI 模式运行 JMete…

堆的创建和说明

文章目录 目录 文章目录 前言 小堆&#xff1a; 大堆&#xff1a; 二、使用步骤 1.创建二叉树 2.修改为堆 3.向上调整 结果实现 总结 前言 我们已经知道了二叉树的样子&#xff0c;但是一般的二叉树是没有什么意义的&#xff0c;所以我们会使用一些特殊的二叉树来进行实现&a…

齿轮端面重合度学习笔记分享

我们知道两个渐开线圆柱齿轮能够正确啮合&#xff0c;他们的基节相等是正常传动的必要但不处分条件。由于轮齿的高度有限&#xff0c;啮合的区间有限&#xff0c;齿轮能否连续传动还要看轮齿对能否及时接替&#xff0c;即前一对轮齿脱离啮合时&#xff0c;后一对轮齿是否已进入…

uniapp结合uview-ui创建项目关键步骤一步一图教程

文章目录 1 构建项目准备工作2 项目创建2.1 打开开发者工具HBuilderX2.2 创建一个新的项目2.3 引入uview-ui组件2.4 uview-ui组件配置2.4.1 uview-ui组件简单介绍2.4.2 修改main.js2.4.3 修改page.json2.4.4 修改App.vue2.4.5 修改uni.scss2.4.6 修改index.vue 2.5 api接口封装…

antv x6使用Vue+ElementPlus实现右键菜单

基于X6官方给出的React版的右键菜单示例&#xff0c;实现Vue版本的&#xff0c;其中右键菜单使用的是ElMenu的样式。 import { ToolsView } from antv/x6 import { h, render } from vue import { ElMenu, ElMenuItem } from element-plus export class ContextMenuTool exten…

公司的Spring框架接受MIME类型为json格式的带null的字符串,然后这个带null的字段被自动忽略了,排查了好久

接收方法&#xff1a; 解决方案&#xff1a; 先去掉RequsetBody 因为使用RequsetBody时&#xff0c;框架会调用HttpMessageConvert读取HttpRequest的InputStram反序列化为对象&#xff0c;这个InputStram只能读一次。 后续你的代码再通过Reader读输入流时&#xff0c;已经没有…

小米SU7对手来了,魅族汽车今年上市

新能源车市场竞争白热化的 2024 年&#xff0c;那些当初一股脑扎堆入场的各路新势力们&#xff0c;估计压根没想到造个车也能这么卷吧&#xff01; 还是那句话&#xff0c;当一个行业开始极度内卷&#xff0c;也就意味着已经到了整个淘汰赛最残酷的环节。 目前来说&#xff0…

相位相关法图像配准

小结&#xff1a;本文主要介绍基于相位相关法的图像配准。 1. 相位相关法 在时域中信号的平移运动可以通过在频域中相位的变化表现出来&#xff08;这是傅里叶变换的特性&#xff0c;见下图&#xff09;。平移不影响傅氏变换的幅值&#xff08;谱&#xff09;&#xff0c;对应…

利用人工智能ChatGPT自动生成基于PO的数据驱动测试框架

简介 PO&#xff08;PageObject&#xff09;设计模式将某个页面的所有元素对象定位和对元素对象的操作封装成一个 Page 类&#xff0c;并以页面为单位来写测试用例&#xff0c;实现页面对象和测试用例的分离。 数据驱动测试&#xff08;DDT&#xff09;是一种方法&#xff0c…

IOday5

一、思维导图 二、练习 使用两个线程完成两个文件的拷贝&#xff0c;分支线程1拷贝前一半&#xff0c;分支线程2拷贝后一半&#xff0c;主线程回收两个分支线程的资源 #include<myhead.h>//定义结构体存储需要传到线程函数中的内容 struct Buf {const char *file[2]; …

Python爬虫:下载人生格言

Python爬虫:下载人生格言 爬取网页 将这些格言下载存储到本地 代码: import requests #导入requests库&#xff0c;用于提取网页 from lxml import etree#导入lxml库&#xff0c;用于Xpath数据解析#请求头 header{ user-agent: Mozilla/5.0 (Windows NT 10.0; Win64; x64) A…

aurora8b10b ip的使用(未完)

文章目录 一、Aurora8B/10B协议二、时钟、复位与状态指示1、时钟2、复位3、状态指示 三、数据发送、接受接口&#xff08;1&#xff09;AXI4-Stream位排序&#xff08;2&#xff09;Streaming接口&#xff08;3&#xff09;Framing接口&#xff08;帧传输接口&#xff09; 四、…

输入成绩问题(c语言)

1.问题&#xff1a;期中考试开始了&#xff0c;大家想要取得好成绩&#xff0c;争夺前五名&#xff0c;从键盘输入n个学生成绩&#xff08;不超过40个&#xff09;&#xff0c;输出每组的前五名的成绩 两行&#xff0c;第一行输入一个整数&#xff0c;表示n个学生&#xff08;…