Spring ) AOP
라이브러리 AspectJ, NameSpaces의 aop
응집도와 관련된 기능, "관심 분리"
<aop:config>
<aop:pointcut id="allPointcut" expression="execution(* com.springbook.biz.*Impl.*(..))"/>
<aop:aspect ref="log">
<aop:before pointcut-ref="allPointcut" method="printLog"/>
</aop:aspect>
</aop:config>
// *(리턴타입 )com.springbook.biz(패키지경로)..*Impl(클래스명).*(..)(함수명, 매개변수)
Joinpoint : 클라이언트가 호출하는 모든 비즈니스 함수
Pointcut : 원하는 특정메소드에서만 공통기능을 수행 시키기 위해서 사용한다.
1. 리턴타입 : *(모든리턴타입), void(void), !void(void가 아닌 리턴타입)
2. 패키지 지정 : ~~biz (~~biz패키지만), ~~biz..(~~biz패키지로 시작하는 모든 패키지),
~~biz..impl (~~biz패키지로 시작하면서 마지막 패키지 이름이 impl로 끝나는 패키지)
3. 클래스 지정 : ~Impl(~Impl 클래스만), *Impl(클래스이름이 Impl로 끝나는 클래스),
~+(~클래스로부터 파생된 모든 자식 클래스)
4. 메소드 지정 : *(..) (모든메소드), get*(..) (get으로 시작하는 메소드)
5. 매개변수 지정 : (..)(제약없이 전부), (*) (1개의 매개변수를 가지는 메소드)
Advice : 공통기능의 코드
Weaving : 메소드가 삽입되는 과정
Aspect : 동작시점 설정
ㄴ Before(실행전), After-Returning(리턴값 오면), After Throwing(에러나면), After(실행 후), Around (실행 전.후 둘다)
// Around는 ProceedingJointPoint객체와 .Proceed(); 메소드가 필요하다.
// ProceedingJointPoint와 .Proceed();는 실행 코드가 실행되지 않도록 잡았다가 Before동작 후 함수가 작동하도록 하며 그 뒤에 after 동작을 한다.
AOP 어노테이션
스프링 설정파일에 <bean>으로 등록하거나 @Service를 통해 컴포넌트가 검색되어야 한다.
@Service
public class LogAdvice {~~}
// <bean id="log" class="com.springbook.~~~"></bean>
@Pointcut("execution(* com.springbook.biz..*Impl.get*(..))")
public void getPointcut() {}
@Pointcut("execution(* com.springbook.biz..*Impl.*(..))")
public void allPointcut() {}
// 포인트 컷 지정이 필요하다.
@Before("지정한 Pointcut 함수")
@AfterReturning, @AfterThrowing, @After, @Around
// 함수 위에 어노테이션 작성
public void printLog() { Syetem.out.println("하고싶은 말"); }
// AfterReturning, AfterThrowing은 바인드 변수를 지정해줘야한다.
// 모두 JoinPoint jp를 매개변수로 받지만 Around만 ProceedingJoinPoint객체를 매개변수로 받는다.
//@Aspect는 (pointcut + advice)역할 @Service밑에 작성하면 된다.
//PointcutCommon class를 만들어서 불필요한 반복을 말을 수 있다.
@Aspect
public class PointcutCommon {
@Pointcut지정
} // ==> @Before("PointcutCommon.allPointcut()") 이런식으로 작성