In everyday development, there are scenarios where we need to retry a method. For example, when making a network call, because of network fluctuation, it is impossible to access, so it is necessary to retry several times.
I. Introduction
gihub: https://github.com/spring-projects/spring-retry
II. Usage
1,Spring-Boot
1. Introducing dependencies
<dependency> <groupId>org.springframework.retry</groupId> <artifactId>spring-retry</artifactId> </dependency>
2. Startup files introduce the @EnableRetry tag, such as
@SpringBootApplication @EnableWebMvc @EnableScheduling @EnableRetry//Open retry mechanism label public class MytestApplication { public static void main(String[] args) { SpringApplication.run(MytestApplication.class, args); } }
3. To retry, add the @Retryable tag, such as
/** * Method to be retried * * @param dto Retry transmission dto * @author lin * @since 2019 September 24th 2013 * <p> * value: To specify an exception to retry, only that exception will be retried. If multiple exceptions are retried, you can write value = {RetryException.class,Exception.class} * maxAttempts: For the number of retries, the default is 3 * @Backeoff Tags in * delay: Delay time (in milliseconds, default is 0 milliseconds) * multiplier: Delay interval multiplier, for example, if the delay is defined as 1 second and the delay multiplier is 2, then the first retry interval is 1 second, the second two seconds, the third four seconds, and so on. * maxDelay: Maximum interval time */ @Retryable(value = RetryException.class, maxAttempts = 5, backoff = @Backoff(delay = 1000, multiplier = 2)) public void handle(RetryTransferDto dto) { log.info("The message is being processed, the current number of times{}Secondly, the message is{}", dto.getCount(), dto.getMessage()); if (true) { // Simulation failure dto.setCount(dto.getCount() + 1); dto.setMessage(dto.getMessage() + " haha "); throw new RetryException("Message processing failed, current number of times" + dto.getCount() + "Secondly, the message is" + dto.getMessage()); } }
In order to facilitate counting, the blogger adds a custom transport class RetryTransferDto. The specific contents of the class are as follows.
import lombok.Data; /** * Retry transmission dto * * @author lin * @since 2019 September 24th 2013 */ @Data public class RetryTransferDto { // retry count private int count = 0; // Retry content private String message; }
4. If you want to enter a specific method to perform certain operations (such as writing a log, etc.) after the last retry, you can use the @Recover tag, for example
/** * Enter this method when the retry reaches the specified number of times * * @author lin * @since 2019 September 24th 2013 */ @Recover public void recover(RetryException e) { log.error("Retry to reach the specified test", e); }
5. The log output is as follows
2019-09-24 10:49:28.572 INFO 2416 --- [ main] com.lin.mytest.retry.RetryService : The message is being processed, the first time in the current number, the message is haha 2019-09-24 10:49:29.575 INFO 2416 --- [ main] com.lin.mytest.retry.RetryService : The message is being processed, the second time in the current number, the message is haha haha 2019-09-24 10:49:31.576 INFO 2416 --- [ main] com.lin.mytest.retry.RetryService : The message is being processed, the third time in the current number, the message is haha haha haha 2019-09-24 10:49:35.577 INFO 2416 --- [ main] com.lin.mytest.retry.RetryService : The message is being processed, the fourth time, the message is haha haha haha haha 2019-09-24 10:49:43.577 INFO 2416 --- [ main] com.lin.mytest.retry.RetryService : The message is being processed for the fifth time, and the message is haha haha haha haha haha 2019-09-24 10:49:43.582 ERROR 2416 --- [ main] com.lin.mytest.retry.RetryService : Retry to reach the specified test org.springframework.retry.RetryException: Message processing failed, current number 6, message haha haha haha haha haha haha at com.lin.mytest.retry.RetryService.handle(RetryService.java:33) ~[classes/:na] ......
Notes
1. because Spring-Retry principle is cut operation, so pom dependency also needs aop dependency.
<dependency> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-starter-aop</artifactId> </dependency>
2. Because it is a tangent operation, the method to be retried cannot be called in the current class. For example, there are methods a and B in class A. When method a calls method b, a retry mechanism is added to method B. This retry method is invalid.
3. maxAttempts, delay, multiplier and other parameters in tags need to be constant. If you want to get it dynamically from the configuration file of yml or properties, use the corresponding Expression parameter. such as
/** * Method to be retried * * @param dto Retry transmission dto * @author lin * @since 2019 September 24th 2013 * <p> * value: To specify an exception to retry, only that exception will be retried. If multiple exceptions are retried, you can write value = {RetryException.class,Exception.class} * maxAttemptsExpression: For the number of retries, the default is 3 * Backeoff Tags in * delayExpression: Delay time (in milliseconds, default is 0 milliseconds) * multiplierExpression: Delay interval multiplier, for example, if the delay is defined as 1 second and the delay multiplier is 2, then the first retry interval is 1 second, the second two seconds, the third four seconds, and so on. * maxDelayExpression: Maximum interval time */ @Retryable(value = RetryException.class, maxAttemptsExpression = "${retry.attempts}", backoff = @Backoff(delayExpression = "${retry.delay}", multiplierExpression = "${retry.multiplier}")) public void handle(RetryTransferDto dto) { log.info("Get parameters from the configuration file, process messages, current number of times{}Secondly, the message is{}", dto.getCount(), dto.getMessage()); if (true) { // Simulation failure dto.setCount(dto.getCount() + 1); dto.setMessage(dto.getMessage() + " haha "); throw new RetryException("Getting parameters from the configuration file, message processing failed, current number of times" + dto.getCount() + "Secondly, the message is" + dto.getMessage()); } }
4. My test code
Code cloud:
https://gitee.com/doubletreelin/mytest.git