: 흩어진 관심사를 모듈화할 수 있는 프로그래밍 기법
OOP 를 보완하는 수단으로 프록시 패턴 을 사용한다.Aspect
Advice 와 어드바이스를 어디에 적용할지를 결정하는 PointCut 을 가지고 있다.Advice
Aspect 가 해야할 일들을 의미한다.PointCut
Advice를 적용할 JoinPoint 를 선별하는 기능을 정의한 모듈을 의미한다.Target
JoinPoint
Advice 가 적용될 수 있는 위치를 의미한다.JoinPoint 는 메서드를 가리킨다 하여도 무방하다.AOP 를 적용할 수 있다.IoC 와 연동하여 엔터프라이즈 애플리케이션에서 가장 흔한 문제에 대한 해결책을 제공하는 것이 목적이다.: 기존 코드의 변경 없이 접근 제어 혹은 부가 기능을 추가할 수 있다.

의존성 추가
<dependency>
    <groupId>org.springframework.boot</groupId>
    <artifactId>spring-boot-starter-aop</artifactId>
</dependency>
Aspect 정의
PointCut 정의
&&||!Advice 정의
예제) 스프링 AOP를 사용하여 메서드 실행시간 로깅하기
// Aspect 에서 어디에 적용할지 표시할 용도로 사용된다.
@Target(ElementType.METHOD)
@Retention(RetentionPolicy.RUNTIME)
public @interface LogExecutionTime { 
    
}
// Service 클래스의 get 메서드나 @LogExecutionTime 애노테이션이 정의된 메서드의 
// 실행시간을 로깅하는 Aspect 구현
@Slf4j
@Aspect
@Component
public class LogAspect {
    @Pointcut("execution(* com..*.*Service.*(..))")
    private void serviceLayer() {}
    @Pointcut("execution(* get*(..))")
    private void getMethod() {}
    @Pointcut("serviceLayer() && getMethod()")
    private void serviceLayerGetMethod() {}
    @Around("serviceLayerGetMethod() || @annotation(LogExecutionTime)")
    public Object logExecutionTime(ProceedingJoinPoint joinPoint) throws Throwable {
        StopWatch stopWatch = new StopWatch();
        stopWatch.start();
        Object proceed = joinPoint.proceed();
        stopWatch.stop();
        log.info(stopWatch.prettyPrint());
        return proceed; 
    }
}