참고
갓대희 [Spring] Filter, Interceptor, AOP 차이 및 정리
우아한 기술 블로그 글을 보다가 AOP를 잘 사용하는 예제를 보게되어 AOP 사용법에 대해 정리해두려고 한다. 내 프로젝트에서도 많이 도움이 될거 같다.
Aspect-Oriented Programming의 약자로 관점 지향 프로그래밍이다. 관점 지향 프로그램은 또 다시 말하면 프로젝트의 코드를 작성하며 반복되는 코드를 흩어진 관심사라고 부르는데 이를 하나의 class로 묶어서 반복되는 코드를 줄여주는 프로그래밍이다.
참고
Spring - AOP 기본개념 및 주요 기능, 예제와 함께 이해하기
implementation 'org.springframework.boot:spring-boot-starter'
implementation 'org.springframework.boot:spring-boot-starter-aop:2.7.0'
aop 기능을 사용할 수 있게 의존성을 우선 추가해준다.
@Aspect
@Component
@Slf4j
public class TestAop {
@Around(value = "execution(* com.example.project.service..*.*(..))")
public Object aroundMethod(ProceedingJoinPoint pjp) throws Throwable {
log.info("method call = {}", pjp.getSignature().toShortString());
Object returnObj = pjp.proceed();
log.info("method complete = {}", pjp.getSignature().toShortString());
return returnObj;
}
}
aop 의존성을 추가하면 @Aspect
와 @Around
ProceedingJoinPoint
를 사용할 수 있다.
@Aspect
aop로 선언
@Around
이 외에 @Before
@After
@AfterReturning
@AfterThrow
등이 있다.
execution()
해당 aop method가 실행될 조건을 적어줄 수 있다.
ProceedingJoinPoint
around로 실행할 경우 ProceedingJoinPoint를 매개변수로 가져올 수 있고 해당 매개변수를 통해 실행되는 method의 정보를 가져올 수 있다.
여기서 중요한 점은
pjp.proceed()
한 return 값을 around에서도 return 해주어야한다는 점이다. 그 이유는 around로 감싸게 되면 메서드의 실행을 가로채서 실행하게 되는 것인데 반환또한 가로채게 된다. 그래서 return에 pjp의 반환값을 넣어주지 않으면 모든 return은 null이 되기 때문에 다음과 같이 작성해주어야한다.
실제로 메서드를 하나 실행시켜보면 다음과 같이 로그로 찍어내는 것을 확인할 수 있다! 앞으로 메서드 실행 로그를 메서드마다 추가하지 않아도 된다!
그림 하나로 설명이 가능한데 filter는 servlet이 시작되기 전 http로 날라온 텍스트 상태일 때 확인해볼 수 있고,
Interceptor는 servlet에 의해 파싱된 데이터들을 가져다가 사용해볼 수 있다.
AOP는 가장 최후에 실행되는 부분으로써 filter와 interceptor보다 좀더 세밀한 부분을 컨트롤할 수 있다.
모니터링
Audit ( 사용자 행위 감시 )
트랜잭션 매니징
토큰 체크
익셉션 핸들링 (Spring에서 제공하는 ControllerAdvice는 AOP가 아님...)
캐싱