AOP : 공통 관심 사항을 구현한 코드를 핵심 코드 안에 삽입하는 방식으로 구현
- 공통 관심사항 : 공통 기능(전체에 적용)
- 핵심 관심사항 : 핵심 로직
● AOP 용어
- Advice : 공통 기능을 담은 모듈, 공통 기능을 동작시킬 시점
동작시점 | 설명 |
Before | 메소드 실행 전에 동작 |
After | 메소드 실행 후에 동작 |
After-returning | 메소드가 정상적으로 실행된 후에 동작 |
After-throwing | 예외가 발생한 후에 동작 (finally 구문) |
Around | 모든 시점에서 동작 |
Around Advice의 경우 joinPoint.Proceed()실행 전은 Before Advice, 실행 후는 After- Advice와 같음
Around = Before + After, After-returning ,After-throwing
- JoinPoint : Advice를 적용 가능한 지점 (메서드호출, 필드값 변경 등)
- PointCut : 실제 Advice가 적용될 JoinPoint, 정규표현식 or AspectJ문법 으로 정의함 / PointCut ⊂ JoinPoint
- Weaving : Advice(공통기능)를 핵심 로직에 적용하는 것(행위)
- Aspect : 어떤 PointCut에 대해 어떤 Advice를 실행할지 결정 / Aspect = Advice + PointCut (가장 큰개념)
● AspectJ 문법(PointCut 표현식)
execution([접근자제어패턴], 리턴타입패턴 [패키지패턴] 메서드이름패턴(파라미터패턴))
- * : 모든값 / ... : 0개 이상
ex) execution(* com.people..*.*(..))
- 접근자제어 : 생략
- 리턴타입 : *
- 패키지 : com.people 패키지와 하위패키지(com.people..)까지 포함한 모든파일 cf) com.people 패키지만 포함할 시 com.people.사용
- 메서드이름 : *
- 파라미터 : ..
●XML
<aop:config> : AOP 설정
<aop:aspect> : Aspect 설정
- ref : 공통 기능의 클래스
<aop:pointcut> : PointCut 설정
- expression : PointCut 표현식
<aop:around> : Around Advice 설정
- pointcut-ref : 적용할 PointCut, method : 적용할 메서드 (Profiler 클래스의 trace()에 적용)
<bean id="profiler" class="ch07.Profiler" />
<aop:config>
<aop:aspect id="traceAspect" ref="profiler">
<aop:pointcut id="publicMethod" expression="execution(public * board..*(..))"/>
<aop:around pointcut-ref="publicMethod" method="trace"/>
</aop:aspect>
</aop:config>
→ Profiler 클래스의 trace()를 publicMethod의 지점에서 Around 시점으로 실행함
● 어노테이션
- xml : <aop:aspectj-autoproxy />
- config : @EnableAspectJAutoProxy 설정
@Aspect : 공통 기능의 클래스(Aspect) 설정
@Pointcut : 적용할 범위(PointCut) 설정
@Around : Around Advice 설정
ex) @Around("execution(* hello.hellospring..*(..))") : hello.hellospring 패키지 아래의 모든 메서드에 적용
@Around("@annocation(LogExecutionTime)") : @LogExecutionTime이 붙은 메서드에 적용
@Around("메서드") : Pointcut을 설정한 메서드
@Aspect
public class ProfilingAspect {
@Pointcut("execution(public * board..*(..))")
private void profileTarget() {}
@Around("profileTarget()")
public Object trace(ProceedingJoinPoint joinPoint) throws Throwable {
String signatureString = joinPoint.getSignature().toShortString();
System.out.println(signatureString + " 시작");
long start = System.currentTimeMillis();
try {
Object result = joinPoint.proceed();
return result;
} finally {
long finish = System.currentTimeMillis();
System.out.println(signatureString + "종료 실행 시간 : " + (finish - start) + "ms");
}
}
}
● 구현
- joinPoint.Proceed() : 핵심 로직을 수행하고 결과값을 Object 타입으로 리턴
Spring은 타겟 객체의 프록시를 만들며 호출시 프록시에 먼저접근
그 후, joinPoint.Proceed()를 통해 실제 타겟 객체인 핵심로직 호출
'Framework > Spring' 카테고리의 다른 글
Mybatis (0) | 2020.09.18 |
---|---|
[JDBC] Mybatis, JPA, Hibernate (0) | 2020.09.18 |
Spring 메이븐 설정 (0) | 2020.09.03 |
Spring MVC (0) | 2020.08.16 |
Spring JDBC (0) | 2020.08.02 |