728x90
반응형
외부 api에 접속할 때 간혹 가다 한 번이 아니라 두세 번 정도 시도를 해야 성공하는 경우가 있다. ( 외부 사이트가 불안정할 경우 )
그럴 때 만들 수 있는 Aspect가 있다. default 값은 꼭 정해주도록 하자.
1. Retry Annotation
backend/annotation/Retry
package web.backend.annotation;
import java.lang.annotation.ElementType;
import java.lang.annotation.Retention;
import java.lang.annotation.RetentionPolicy;
import java.lang.annotation.Target;
@Target(ElementType.METHOD)
@Retention(RetentionPolicy.RUNTIME)
public @interface Retry {
int value() default 3;
}
2. RetryAspect
backend/aop/RetryAspect
package web.backend.aop;
import lombok.extern.slf4j.Slf4j;
import org.aspectj.lang.ProceedingJoinPoint;
import org.aspectj.lang.annotation.Around;
import org.aspectj.lang.annotation.Aspect;
import web.backend.annotation.Retry;
@Slf4j
@Aspect
public class RetryAspect {
@Around("@annotation(retry)")
public Object doRetry(ProceedingJoinPoint joinPoint, Retry retry) throws Throwable {
log.info("[retry] {} retry={} ", joinPoint.getSignature(), retry);
int maxRetry = retry.value();
Exception exceptionHolder = null;
for (int retryCount = 1; retryCount <= maxRetry; retryCount++) {
try {
log.info("[retry] try count={}/{}", retryCount, maxRetry);
return joinPoint.proceed();
} catch (Exception e) {
exceptionHolder = e;
}
}
throw exceptionHolder;
}
}
3. AopConfig
backend/aop/AopConfig
...
@Bean
public RetryAspect retryAspect() { return new RetryAspect(); }
...
테스트
Service 부분을 잠시 바꿔보고 해보자.
backend/module/user/UserService
...
private static int seq = 0;
@Retry(value = 2)
public String save(User user) {
if (seq == 0) {
seq++;
throw new IllegalStateException("예외 발생!!");
}
return "ok";
}
...
실행 결과
728x90
반응형