- 공통 관심 사항과 핵심 관심 사항 코드가 섞이면 유지보수가 어렵고 불편함
AOP
- aspect oriented programming
- 공통 관심 사항 - 핵심 관심 사항 분리
TimeTraceAop
package hello.hellospring.aop;
import org.aspectj.lang.ProceedingJoinPoint;
import org.aspectj.lang.annotation.Around;
import org.aspectj.lang.annotation.Aspect;
import org.springframework.stereotype.Component;
@Aspect //AOP에 달아줘야함
@Component //컴포넌트 스캔으로 빈에 등록하기 위함
public class TimeTraceAop {
@Around("execution(* hello.hellospring..*(..))")
public Object execute(ProceedingJoinPoint joinPoint) throws Throwable{
long start = System.currentTimeMillis();
System.out.println("START : "+joinPoint.toString());
try{
//다음 메소드로 진행, 참고 ctrl alt shift t : refactor this 단축키
return joinPoint.proceed();
} finally {
long finish = System.currentTimeMillis();
long timeMs = finish-start;
System.out.println("END : "+joinPoint.toString()+" "+timeMs+"ms");
}
}
}
- aop 패키지 만들고 작성함
@Aspect
: aop 에 달아줘야함
@Component
: 컴포넌트 스캔으로 빈에 등록하기 위함. 이 방식을 안쓰고 SpringConfig 파일에 @Bean
으로 등록할 수도 있음. @Bean
으로 등록하는 방식이 AOP가 특별한 클래스이기 때문에 그걸 config 파일을 보고 인지하기 좋아서 더 추천한다고 함
@Around
: 적용 대상을 정함
joinPoint.proceed()
: 다음 메소드로 넘어감
SpringConfig
// @Bean
// public TimeTraceAop timeTraceAop(){
// return new TimeTraceAop();
// }
- 위 내용을 SpringConfig에 추가해서 빈으로 등록할 수도 있음
- AOP는 실제 객체 대신 proxy를 앞에 세워서 proxy가
joinPoint.proceed()
로 실제 객체를 호출하는 방식으로 작동함