지난시간에는 xml을 통해 포인트컷과 애스펙트를 설정하는 방법을 배웠다
이제 스프링 부트에서 사용하는 어노테이션을 사용하여 어드바이스를 실행시키고자한다
✔️설정 방법
1. 오토프록시 설정하기
기존 xml에 오토프록시라는것을 추가해준다 이 오토프록시가 추가됨으로 인해서 어노테이션의 사용이 가능해진다
xml에 있던 기존 코드는 주석으로 가려준다 xml에서 주석사용을 권장하지는 않는다
<aop:aspectj-autoproxy/> //AOP 사용을 위한 설정
2. 기존 bean 태그를 어노테이션으로 변경
기존에는 XML의 <bean> 태그를 통해 어드바이스 객체를 스프링 컨테이너에 등록하였다.
이를 어노테이션 기반 설정으로 변경하면, 어드바이스 클래스에 @Component를 적용하여 동일한 역할을 수행할 수 있다.
@Component는 스프링이 해당 클래스를 빈으로 인식하도록 만드는 가장 기본적인 어노테이션으로,
XML의 <bean> 태그를 대체하는 역할을 한다.
한편, 횡단 관심사를 핵심 관심사에 적용하는 행위를 위빙(Weaving) 이라고 한다.
AOP 관점에서 보면 어드바이스는 횡단 관심사이며,
현재 프로젝트에서 이 횡단 관심사가 적용되는 대상은 서비스(Service) 계층의 메서드이다.
이 때문에 어드바이스 클래스에 @Service 어노테이션을 적용해야한다
xml 설정
<bean class="com.example.biz.common.LogAdvice" id="la" />
어노테이션
@service // 빈태그를 대신한다
public class LogAdvice {
}
3. 포인트컷 설정하기
xml의 설정을 모두 주석처리해주었으니 로그 어드바이스에서 포인트컷을 설정해줘야한다
기존 XML설정
<aop:pointcut expression="execution(* com.example.biz..*Impl.*(..))" id="aPointcut" />
<aop:pointcut expression="execution(* com.example.biz..*Impl.get*(..))" id="bPointcut" />
@PointCut 정의하기
@Service
public class LogAdvice {
//ServiceImpl 계열 메서드를 대상으로 하는 포인트컷 정의
@Pointcut("execution(* com.example.biz..*Impl.*(..))")
@Pointcut("execution(* com.example.biz..*Impl.get*(..)")
//포인트컷에 이름을 부여하기 위한 메서드 (실행 로직 없음)
public void aPointCut(){}
public void bPointcut() {}
public void printLog() {
System.out.println("꼬부기님의 로그");
}
}
4.애스펙트 만들기
애스펙트는 포인트컷과 어드바이스를 합친것이다
기존 xml 설정
<aop:aspect ref="pla">
<aop:before method="printLog" pointcut-ref="aPointcut" />
</aop:aspect>
로그 어드바이스에서 @service위에 @Aspect를 설정해준다 그리고 핵심 관심사 위에 @동작시점과 포인트컷의 이름을 적는다
@Aspect는 안적어도 실행시키는데 문제는 없으나 가독성과 공통으로 사용하는 코드를 중요시해야한다는 점에서 적는것이 더 좋다
@Aspect // 애스팩트 설정하기
@Service
public class LogAdvice {
@Pointcut("execution(* com.example.biz..*Impl.*(..))")
@Pointcut("execution(* com.example.biz..*Impl.get*(..)")
public void aPointCut(){}
public void bPointcut() {}
@Before("aPointcut()")// 동작시점과 포인트컷이름 작성
public void printLog() {
System.out.println("꼬부기님의 로그");
}
}
바인드 변수를 사용하는 애프터리터닝과 애프터쓰로잉은 설정방법이 살짝 다르다
기존 xml 설정
<aop:aspect ref="ara">
<aop:after-returning method="printLog" pointcut-ref="bPointcut" returning="returnObj" />
</aop:aspect>
포인트컷 이름 옆에 바인드 변수로 사용한 이름을 지정해주었다
@AfterReturning 어노테이션을 사용하여 설정할수 있다 이때 포인트컷의 이름과 사용한 바인드변수명을 지정해줘야한다 즉 xml의 설정과 같다
@Aspect
@Service
public class AfterReturningAdvice {
@Pointcut("execution(* com.example.biz..*Impl.*(..))")
@Pointcut("execution(* com.example.biz..*Impl.get*(..)")
public void aPointCut(){}
public void bPointcut() {}
@AfterReturning(pointcut="bPointcut()", returning="returnObj")
// xml의 설정과 똑같이 사용한 바인드 변수명을 알려줘야한다
public void printLog(JoinPoint jp, Object returnObj) {
}
🛠️포인트컷 분리하여 새로 클래스만들기
현재 코드에는 포인트컷 정의가 중복되어있다 따라서 포인트컷만 관리하는 클래스를 만들어 따로 관리할것이다
포인트컷 커먼이라는 클래스를 만든다 여기에 @Aspect 어노테이션을 설정해주고 포인트컷을 정의한뒤 기존코드에 있던 포인트 컷을 모두 삭제한다
@Aspect
public class PointcutCommon { // 포인트컷만 관리하는 클래스
@Pointcut("execution(* com.example.biz..*Impl.*(..))")
public void aPointcut() {}
@Pointcut("execution(* com.example.biz..*Impl.get*(..))")
public void bPointcut() {}
}
포인트컷만 관리하는 하나의 클래스를 만들었으므로 어드바이스에 클래스의 이름을 추가해 포인트컷이 있는 위치를 알려주어야한다
@Aspect
@Service
public class LogAdvice {
@Before("PointcutCommon.aPointcut()")
'🐢 꼬부기 LV.1 | 개념•기초 > 💧물대포(핵심개념)' 카테고리의 다른 글
| JDBCtemplate 문법 (0) | 2026.01.28 |
|---|---|
| JDBC템플릿 구조 (0) | 2026.01.28 |
| 어드바이스 사용해보기 (0) | 2026.01.26 |
| AOP 설정 및 사용 (0) | 2026.01.23 |
| AOP 용어 정리 (0) | 2026.01.23 |