애스펙트 정의하기
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 | @Aspect public class Audience { @Before("execution(** concert.Performance.perform(..))") public void silenceCellPhones () { System.out.println("휴대폰을 매너 모드로 변경한다."); } @Before("execution(** concert.Performance.perform(..))") public void takeSeats () { System.out.println("자리에 앉는다."); } @AfterReturning("execution(** concert.Performance.perforn(..))") public void appaluse () { System.out.println("짝! 짝! 짝!"); } @AfterThrowing("execution(** concert.Performance.perform(..))") public void demandRefund () { System.out.println("환불을 요구한다."); } } | cs |
감이 오는가? 네 개의 메서드는 concert.Performance 클래스의 perform() 메서드가 동작할 때, AOP로서 각각 동작한다.
perform() 메서드가 실행되기 전에 silenceCellPhones(), takeSeats() 메서드가 실행되고, perform() 메서드의 동작이 완료되면 appaluse() 메서드가, Exception이 발생하면 demandRefund() 메서드가 동작한다.
스프링은 AspectJ 어노테이션 다섯개를 제공하는데, 다음과 같다.
어노테이션 |
어드바이스 |
@After |
어드바이스 메서드는 어드바이스된 메서드가 반환되거나 예외 상황이 발생한 이후에 호출된다. |
@AfterReturning |
어드바이스 메서드는 어드바이스된 메서드가 반환된 이후에 호출된다. |
@AfterThrowing |
어드바이스 메서드는 어드바이스된 메서드가 예외 상황을 발생시킨 이후에 호출된다. |
@Around |
어드바이스 메서드는 어드바이스된 메서드를 감싼다. |
@Before |
어드바이스 메서드는 어드바이스된 메서드가 호출되기 이전에 호출된다. |
위 코드에서 execution 표현식에 반복되는 부분이 거슬린다. 좀 더 편하게 사용하는 방법은 없을까?
@Pointcut 어노테이션을 사용하면 AspectJ 어노테이션에서 재사용 가능한 포인트컷을 정의할 수 있다.
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 | @Aspect public class Audience { @Pointcut("execution(** concert.Performance.perform(..))") public void performance() {} @Before("performance()") public void silenceCellPhones () { System.out.println("휴대폰을 매너 모드로 변경한다."); } @Before("performance()") public void takeSeats () { System.out.println("자리에 앉는다."); } @AfterReturning("performance()") public void appaluse () { System.out.println("짝! 짝! 짝!"); } @AfterThrowing("performance()") public void demandRefund () { System.out.println("환불을 요구한다."); } } | cs |
이 때 performance() 메서드의 몸체는 신경쓸 필요가 없고, 마커라고 생각하면된다.
그리고 이 AspectJ 어노테이션을 해석하는 설정을 해야하는데, JavaConfig에서는 다음과 같이 설정한다.
1 2 3 4 5 6 7 8 9 10 11 12 | @Configuration @EnableAspectJAutoProxy @ComponentScan public class ConcertConfig { @Bean public Audience audience () { return new Audience(); } } | cs |
XML에서는 아래와 같이 설정하면된다.
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 | <beans xmls="http://www.springframework.org/schema/beans" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:context="http://www.springframework.org/schema/context" xmlns:aop="http://www.springframework.org/schema/aop" xsi:schemaLocation="http://www.springframework.org/schema/aop http://www.springframework.org/schema/aop/spring-aop.xsd http://www.springframework.org/schema/context http://www.springframewokr.org/schema/context/spring-context.xsd http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd"> <context:component-scan base-package="concert" /> <aop:aspectj-autoproxy /> <bean class="concert.Audience" /> </beans> | cs |
|
이 포스트는 스프링 인 액션을 읽고 개인적으로 필요하다고 생각되는 내용을 정리한 포스트입니다. 일부 내용, 소스코드는 스프링 인 액션의 내용일 수 있습니다. |
'🌱 SPRING > 스프링 인 액션' 카테고리의 다른 글
어드바이스에서 파라메터 처리 (0) | 2018.05.26 |
---|---|
@Around (0) | 2018.05.26 |
포인트 커트를 이용한 조인 포인트 선택 (0) | 2018.05.26 |
AOP란? (0) | 2018.05.24 |
조건부 빈 (0) | 2018.05.21 |