SpringBoot高并发!业务方法重试就该使用它

开发 前端
Fast-Retry是一个高性能任务重试框架,支持百万级别任务的并发重试处理。与主流的Spring-Retry, Guava-Retry等同步重试框架不同,Fast-Retry是一个支持异步重试框架,支持异步任务的重试、超时等待、回调。

环境:SpringBoot3.2.5

1. 简介

业务功能重试机制通常在项目中是非常有必要的,特别是在处理外部系统调用(如HTTP请求、数据库操作、消息队列等)时。这些操作可能因网络波动、服务暂时不可用等原因而失败。重试机制可以提高系统的健壮性和用户体验,通过自动重试可以减少因单次失败导致的整体业务中断。本篇文章将介绍一款非常优秀的重试框架Fast-Retry。

Fast-Retry是一个高性能任务重试框架,支持百万级别任务的并发重试处理。与主流的Spring-Retry, Guava-Retry等同步重试框架不同,Fast-Retry是一个支持异步重试框架,支持异步任务的重试、超时等待、回调。Spring-Retry, Guava-Retry均无法支持大批量任务的重试,因为会占用过多线程资源导致大量任务在等待处理,随着任务数的增加,系统吞吐量大大降低,性能指数级降低,Fast-Retry的性能是前者的指数倍。

Fast-Retry,Spring-Retry,Guava-Retry性能对比

测试条件

  • 测试线程池: 8个固定线程
  • 单个任务逻辑: 轮询5次,隔2秒重试一次,总耗时10秒
  • 未测预计公式:当我们使用线程池的时候, 一般线程池中 总任务处理耗时 = 任务数/并发度 x 单个任务重试耗时

图片图片

2. 实战案例

2.1 引入依赖

<dependency>
  <groupId>io.github.burukeyou</groupId>
  <artifactId>fast-retry-all</artifactId>
  <version>0.2.0</version>
</dependency>

配置开启重试功能

@SpringBootApplication
@EnableFastRetry
public class SpringbootRetryApplication {}

接下来就可以通过@FastRetry注解配置类或方法。

2.2 基于编程重试

public String process() throws Exception {
  // 自定义结果重试策略,如果返回结果不是"success"则进行重试
  RetryResultPolicy<String> resultPolicy = result -> !result.equals("success");
  FastRetryer<String> retryer = FastRetryBuilder.<String>builder()
      // 重试次数
      .attemptMaxTimes(2)
       // 重试间隔
      .waitRetryTime(1, TimeUnit.SECONDS)
      // 发生异常后是否重试
      .retryIfException(true)
      // 什么类型的异常进行重试
      .retryIfExceptionOfType(RuntimeException.class)
      .exceptionRecover(true)
      // 自定义结果重试策略
      .resultPolicy(resultPolicy)
      .build();
  CompletableFuture<String> future = retryer.submit(() -> {
    int r = new Random().nextInt(10) ;
    System.out.printf("执行业务方法, 随机值: %d%n", r) ;
    if (r != 1) {
      // 抛出异常,也会重试
      // throw new RuntimeException("错误的参数: " + r) ;
      return "dead" ;
    }
    return "success" ;
  });
  return future.get();
}

运行结果

成功

执行业务方法, 随机值: 5
执行业务方法, 随机值: 4
执行业务方法, 随机值: 1
结果: success

失败

图片图片

超过重试次数后抛出异常,并且方法执行的最终结果返回:null。

2.3 基于注解

基于注解方式使用起来与spring-retry差不多。一个注解搞定。

@FastRetry(
  retryWait = @RetryWait(delay = 2), 
  exceptionRecover = false, 
  maxAttempts = 2,
  retryStrategy = PackRetryPolicy.class
)
public String business(Long id, String name) {
  int r = new Random().nextInt(10) ;
  System.out.printf("执行业务方法, 随机值: %d%n", r) ;
  if (r != 1) {
    throw new RuntimeException("错误的参数: " + r) ;
  }
  return "success" ;
}

自定义方法返回结果重试策略。

public class PackRetryPolicy implements RetryResultPolicy<String> {
  public boolean canRetry(String t) {
    return !t.equals("success") ;
  }
}

结果重试策略可以有多个。

2.4 异步任务重试

@FastRetry(
  retryWait = @RetryWait(delay = 2), 
  maxAttempts = 2, 
  retryStrategy = PackRetryPolicy.class
)
public CompletableFuture<String> asyncBusiness(Long id, String name) {
  return CompletableFuture.supplyAsync(() -> {
    System.out.println("async 执行业务方法...") ;
    int r = new Random().nextInt(10) ;
    if (r != 1) {
      // throw new RuntimeException("错误的参数: " + r) ;
      return "1" ;
    }
    return "success" ;
  }) ;
}

输出结果

async 执行业务方法...
async 执行业务方法...
async 执行业务方法...
发生错误: com.burukeyou.retry.core.exceptions.FastRetryTimeOutException: 
  The maximum retry count has been exceeded after 2 times. Stop retry

同样的代码,如果换成spring-retry,如下:

// spring-retry的注解
@Retryable(maxAttempts = 2)
public CompletableFuture<String> asyncBusiness(Long id, String name) {
  // 方法体与上面基本,一样只不过其中抛出的是异常
}

输出结果

async 执行业务方法...
发生错误: java.lang.RuntimeException: 错误的参数: 3

没有进行重试,说明spring-retry不支持异步任务。

在spring-retry中你可以在注解中配置recover,指定一个恢复的方法(或降级的方法),在fast-retry中没有这样的功能。如下spring-retry示例:

@Retryable(maxAttempts = 2, recover = "businessRecover")
public String business(Long id, String name) {}
@Recover
private String businessRecover(Throwable th, Long id, String name) {}

当重试次数用尽后,将调用我们这里配置的businessRecover方法,同时在该方法中还可以获取具体的异常信息。

责任编辑:武晓燕 来源: Spring全家桶实战案例源码
相关推荐

2023-09-25 08:06:44

工具非阻塞式接口

2024-01-04 18:01:55

高并发SpringBoot

2021-03-11 08:00:00

存储数据SSD

2021-12-27 07:59:11

Web3区块链协议

2021-03-12 18:25:09

开发前端React

2024-09-10 10:42:27

2018-10-23 10:28:01

服务器流量高并发

2018-09-11 08:37:05

高并发服务器优化

2023-10-23 11:40:44

SpringBootDisruptor

2022-11-21 06:40:23

微服务架构

2017-11-13 11:07:32

Nginx搭建高可用

2020-10-28 07:10:07

Nginx高可用高并发

2019-06-28 10:55:04

预热高并发并发高

2024-01-05 18:01:17

高并发策略程序

2019-04-16 15:40:48

Java架构高并发

2020-04-10 10:10:28

Nginx高并发性能

2022-03-01 16:58:25

业务预测模型

2012-02-06 09:59:16

苹果iPhone微软

2022-09-15 08:41:16

数据异构分库分表

2023-07-05 13:58:10

权限模型设计模式
点赞
收藏

51CTO技术栈公众号