Spring提供了重试的功能,使用非常的简单、优雅。
<!--Spring重试模块-->
<dependency>
<groupId>org.springframework.retry</groupId>
<artifactId>spring-retry</artifactId>
</dependency>
<dependency>
<groupId>org.aspectj</groupId>
<artifactId>aspectjweaver</artifactId>
</dependency>
import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;
import org.springframework.retry.annotation.EnableRetry;
@EnableRetry
public class HuanXinDubboApplication {
public static void main(String[] args) {
SpringApplication.run(HuanXinDubboApplication.class, args);
}
}
import cn.hutool.core.util.RandomUtil;
import org.springframework.retry.annotation.Backoff;
import org.springframework.retry.annotation.Recover;
import org.springframework.retry.annotation.Retryable;
import org.springframework.stereotype.Service;
@Service
public class RetryService {
@Retryable(value = RuntimeException.class, maxAttempts = 3, backoff = @Backoff(delay = 2000L, multiplier = 2))
public int execute(int max) {
int data = RandomUtil.randomInt(1, 99);
System.out.println("生成:" + data);
if (data < max) {
throw new RuntimeException();
}
return data;
}
@Recover //全部重试失败后执行
public int recover(Exception e) {
System.out.println("全部重试完成。。。。。");
return 88; //返回默认
}
}
@Retryable参数说明:
-
value:抛出指定异常才会重试
-
maxAttempts:最大重试次数,默认3次
-
backoff:重试等待策略,默认使用@Backoff
- @Backoff 的value默认为1000L,我们设置为2000L;
- multiplier(指定延迟倍数)默认为0,表示固定暂停1秒后进行重试,如果把multiplier设置为2,则第一次重试为2秒,第二次为4秒,第三次为6秒。
@Recover标注的方法,是在所有的重试都失败的情况下,最后执行该方法,该方法有2个要求:
- 方法的第一个参数必须是 Throwable 类型,最好与 @Retryable 中的 value一致。
- 方法的返回值必须与@Retryable的方法返回值一致,否则该方法不能被执行。
测试类:
import org.junit.Test;
import org.junit.runner.RunWith;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.boot.test.context.SpringBootTest;
import org.springframework.test.context.junit4.SpringRunner;
@SpringBootTest
@RunWith(SpringRunner.class)
public class TestRetryService {
@Autowired
private RetryService retryService;
@Test
public void testRetry() {
System.out.println(this.retryService.execute(90));
}
}