服务器之家:专注于服务器技术及软件下载分享
分类导航

PHP教程|ASP.NET教程|JAVA教程|ASP教程|编程技术|正则表达式|

服务器之家 - 编程语言 - JAVA教程 - 浅谈spring的重试机制无效@Retryable@EnableRetry

浅谈spring的重试机制无效@Retryable@EnableRetry

2020-09-18 14:10Singlerr JAVA教程

这篇文章主要介绍了浅谈spring的重试机制无效@Retryable@EnableRetry,具有很好的参考价值,希望对大家有所帮助。一起跟随小编过来看看吧

spring-retry模块支持方法和类、接口、枚举级别的重试

方式很简单,引入pom包

?
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
<parent>
  <groupId>org.springframework.boot</groupId>
  <artifactId>spring-boot-starter-parent</artifactId>
  <version>lastest</version>
</parent>
<dependency>
  <groupId>org.springframework.boot</groupId>
  <artifactId>spring-boot-starter-web</artifactId>
</dependency>
<!-- https://mvnrepository.com/artifact/org.springframework.retry/spring-retry -->
<dependency>
  <groupId>org.springframework.retry</groupId>
  <artifactId>spring-retry</artifactId>
  <version>1.1.2.RELEASE</version>
</dependency>
<dependency>
  <groupId>org.aspectj</groupId>
  <artifactId>aspectjweaver</artifactId>
  <version>1.8.6</version>
</dependency>

然后在@Configuration注解的类中添加@EnableRetry

最后在想要重试的方法上添加@Retryable(Exception.class)

由于retry用到了aspect增强,所有会有aspect的坑,就是方法内部调用,会使aspect增强失效,那么retry当然也会失效。

例如

?
1
2
3
4
5
6
7
8
9
10
public class demo {
  public void A() {
    B();
  }
 
  @Retryable(Exception.class)
  public void B() {
    throw new RuntimeException("retry...");
  }
}

 

这种情况B()不会重试。

补充知识:Springboot整合Spring Retry实现重试机制

在项目开发过程中,经常会有这样的情况:第一次执行一个操作不成功,考虑到可能是网络原因造成,就多执行几次操作,直到得到想要的结果为止,这就是重试机制。

Springboot可以通过整合Spring Retry框架实现重试。

下面讲一下在之前新建的ibatis项目基础上整合Spring Retry框架的步骤:

1、首先要在pom.xml配置中加入spring-retry的依赖:

?
1
2
3
4
5
6
7
8
<dependency>
  <groupId>org.springframework.retry</groupId>
  <artifactId>spring-retry</artifactId>
</dependency>
<dependency>
  <groupId>org.aspectj</groupId>
  <artifactId>aspectjweaver</artifactId>
</dependency>

2、在启动类中加入重试注解@EnableRetry。

?
1
2
3
4
5
6
7
8
9
10
11
12
13
import org.mybatis.spring.annotation.MapperScan;
import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;
import org.springframework.retry.annotation.EnableRetry;
 
@EnableRetry //重试注解
@MapperScan("com.batis.mapper")
@SpringBootApplication
public class BatisApplication {
  public static void main(String[] args) {
    SpringApplication.run(BatisApplication.class, args);
  }
}

3、新建重试接口RetryService和实现类RetryServiceImpl

重试接口:

?
1
2
3
public interface RetryService {
  void retryTransferAccounts(int fromAccountId, int toAccountId, float money) throws Exception;
}

接口实现类:

?
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
import com.batis.mapper.AccountMapper;
import com.batis.model.Account;
import com.batis.service.RetryService;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.retry.annotation.Backoff;
import org.springframework.retry.annotation.Recover;
import org.springframework.retry.annotation.Retryable;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;
 
@Service
public class RetryServiceImpl implements RetryService {
  @Autowired
  private AccountMapper accountMapper;
 
  @Transactional
  @Retryable(value = Exception.class, maxAttempts = 3, backoff = @Backoff(delay = 3000, multiplier = 1, maxDelay = 10000))
  @Override
  public void retryTransferAccounts(int fromAccountId, int toAccountId, float money) throws Exception {
    Account fromAccount = accountMapper.findOne(fromAccountId);
    fromAccount.setBalance(fromAccount.getBalance() - money);
    accountMapper.update(fromAccount);
 
    int a = 2 / 0;
    Account toAccount = accountMapper.findOne(toAccountId);
    toAccount.setBalance(toAccount.getBalance() + money);
    accountMapper.update(toAccount);
    throw new Exception();
  }
 
  @Recover
  public void recover(Exception e) {
    System.out.println("回调方法执行!!!");
  }
}

@Retryable:标记当前方法会使用重试机制

value:重试的触发机制,当遇到Exception异常的时候,会触发重试

maxAttempts:重试次数(包括第一次调用)

delay:重试的间隔时间

multiplier:delay时间的间隔倍数

maxDelay:重试次数之间的最大时间间隔,默认为0,如果小于delay的设置,则默认为30000L

@Recover:标记方法为回调方法,传参与@Retryable的value值需一致

4、新建重试控制器类RetryController

?
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
import com.batis.service.RetryService;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RequestMethod;
import org.springframework.web.bind.annotation.RestController;
 
@RestController
@RequestMapping("/retry")
public class RetryController {
  @Autowired
  private RetryService retryService;
 
  @RequestMapping(value = "/transfer", method = RequestMethod.GET)
  public String transferAccounts() {
    try {
      retryService.retryTransferAccounts(1, 2, 200);
      return "ok";
    } catch (Exception e) {
      return "no";
    }
  }
}

5、启动ibatis项目进行测试,在浏览器地址栏输入:http://localhost:8080/retry/transfer

浅谈spring的重试机制无效@Retryable@EnableRetry

可以看到,转账操作一共执行了3次,最后执行了回调方法。

至此Springboot整合Spring Retry的步骤已经完成,测试也非常成功!

有可以改进的地方希望诸位同学不要吝惜笔墨,加以指正,万分感谢!

以上这篇浅谈spring的重试机制无效@Retryable@EnableRetry就是小编分享给大家的全部内容了,希望能给大家一个参考,也希望大家多多支持服务器之家。

原文链接:https://blog.csdn.net/xsgnzb/article/details/78780795

延伸 · 阅读

精彩推荐
  • JAVA教程30条Java代码编写经验分享

    30条Java代码编写经验分享

    你知道写好Java代码的30条经验是什么吗?这篇文章主要为大家分享了30条Java代码编写经验技巧,具有一定的参考价值,感兴趣的小伙伴们可以参考一下...

    Java开发-搁浅4672020-08-11
  • JAVA教程详解Java中的迭代器Iterator与枚举器Enumeration

    详解Java中的迭代器Iterator与枚举器Enumeration

    Iterator与Enumeration分别是实现迭代器和枚举器类的接口,下面就带大家来详解Java中的迭代迭代器Iterator与枚举器Enumeration,以及它们之间的区别. ...

    kuiwu-wang3772020-05-04
  • JAVA教程详解Java注解教程及自定义注解

    详解Java注解教程及自定义注解

    这篇文章主要为大家详细介绍了Java注解教程及自定义注解,帮助大家更好地学习Java注解,感兴趣的小伙伴们可以参考一下 ...

    lijiao2582020-03-24
  • JAVA教程使用Java对数据库进行基本的查询和更新操作

    使用Java对数据库进行基本的查询和更新操作

    这篇文章主要介绍了使用Java对数据库进行基本的查询和更新操作,是Java入门学习中的基础知识,需要的朋友可以参考下 ...

    goldensun3572020-01-09
  • JAVA教程java中for循环删除集合陷阱

    java中for循环删除集合陷阱

    java中在增强for循环为什么不能增删集合呢?一个循环迭代,跟集合的增删改没什么关系。修改集合不是for去做的。for只管循环迭代,你在循环里边修改集合...

    hebedich4712019-12-17
  • JAVA教程常用Eclipse快捷方式(推荐)

    常用Eclipse快捷方式(推荐)

    下面小编就为大家带来一篇常用Eclipse快捷方式(推荐)。小编觉得挺不错的,现在就分享给大家,也给大家做个参考。一起跟随小编过来看看吧 ...

    jingxian2622020-05-08
  • JAVA教程java生成彩色附logo二维码

    java生成彩色附logo二维码

    这篇文章主要为大家介绍了java生成带logo的多彩二维码,比一般二维码颜色鲜艳,美观,如何生成二维码,下面小编为大家分享实现代码,感兴趣的小伙伴...

    lijiao3992020-04-17
  • JAVA教程java获取登录者IP和登录时间的两种实现代码详解

    java获取登录者IP和登录时间的两种实现代码详解

    这篇文章主要介绍了java获取登录者IP和登录时间的实现代码,本文通过两种结合实例代码给大家介绍的非常详细,对大家的学习或工作具有一定的参考借鉴...

    心寒丶1802020-07-21