-
스프링 AOP (스프링 핵심 기술 - 5)Programming/Spring Framework 주요 개념 2020. 3. 5. 00:43728x90
1. AOP (Aspect-Oriented Programming) 이란?
- OOP를 보완하는 수단으로, 흩어진 Aspect를 모듈화 할 수 있는 프로그래밍 기법
- 흩어진 관심사들을 하나로 모아서 Aspect로 모듈화하는 기법
2. 주요 개념
- Aspect : 모듈
- Target : 적용되는 대상 (Class A, B)
- Advice : 해야할 일
- Join Point : 합류 지점 (생성자 호출 전, 메소드를 호출하기 전, 필드에서 값을 가져갈 때...)
- Pointcut : 어디에 적용되어야 하는지
3. 구현체
- AspectJ (다양한 Join Point를 사용해야 할 때)
- 스프링 AOP
- 둘을 연동해서 사용 가능
3. 적용 방법
- 컴파일 타임 : 컴파일 할 때, 조작된 자바 바이트 코드를 생성 (AspectJ 컴파일러)
- 로드 타임 : 바이트 코드를 로드할 때 생성 (AspectJ 사용)
- 런타임 : A객체 빈을 만들 때, 이를 감싸는 proxy 빈을 만듬 (스프링 AOP 사용 - 합리적이고, 자주 쓰게될 방법)
4. 스프링AOP
- 프록시 기반의 AOP 구현체
- 스프링 빈에만 AOP를 적용할 수 있다
프록시 패턴
- 왜 프록시 패턴 사용? 기존 코드 변경 없이 접근 제어 또는 부가 기능 추가
- Proxy는 RealSubject를 참조하며 이 기능 + 추가적인 기능을 수행함.
- Client와 RealSubject 코드의 변경없이 기능 추가
- 매번 프록시 클래스 생성, 객체들 관계 복잡 등 문제 있음 따라서 스프링 AOP 등장
스프링AOP
- 스프링 IoC컨테이너가 제공하는 기반 시설과 Dynamic 프록시를 사용하여 복잡한 문제 해결
- 동적 프록시 (동적으로 프록시 객체를 생성)
- 스프링 IoC의 AbstractAutoProxyCreator(BeanPostConstruct를 상속)는 기존 빈을 대체하는 동적 프록시 빈을 만들 어 등록 시켜줌
5. @AOP
- 어노테이션 기반의 @AOP
1. 의존성 추가
<dependency> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-starter-aop</artifactId> </dependency>
2. Aspect 정의
@Component @Aspect public class PerfAspect { // 어디에 적용할 것인가 (포인트 컷) @Around("@annotation(PerfLogging)") // 해야할 일 (어드바이스) public Object logPerf(ProceedingJoinPoint pjp) throws Throwable { // pjp 는 적용되는 부분으로 (메소드 그 자체) long begin = System.currentTimeMillis(); Object retVal = pjp.proceed(); System.out.println(System.currentTimeMillis() - begin); return retVal; } @Before("bean(simpleEventService)") public void printHello(){ System.out.println("Hello~"); } }
3. 어노테이션 정의
/* 이 어노테이션을 사용하면 성능을 측정해줍니다. */ @Documented @Target(ElementType.METHOD) @Retention(RetentionPolicy.CLASS) public @interface PerfLogging { }
참고)
// 인터페이스 타입인 경우 인터페이스로 주입 받는 것을 권장함 @Autowired EventService eventService; /* 실무에서 우려되는 부분은 인터페이스를 쓰지 않을 때 다음과 같은 복잡한 문제가 생길 수 있음 인터페이스를 기반으로 프록시 객체를 만들도록 설정하면 MyService -> DefaultMyService MyService -> ProxyService ProxyService 는 DefaultMyService 와 상속관계가 아니므로 불러올 수 없음 스프링 부트는 default로 클래스를 기반으로 프록시 객체를 만듬 MyService -> DefaultMyService -> ProxyService */
// 이렇게 같은 타입으로 지정하거나, 같은 클래스 이름으로 지정하면 해당 빈을 주입받을 수 있음 @Autowired SimpleEventService simpleEventService; @Autowired EventService simpleEventService;
인프런 백기선님 '스프링 프레임워크 핵심 기술' 강의를 듣고 정리한 내용입니다.
728x90'Programming > Spring Framework 주요 개념' 카테고리의 다른 글
Spring Application (스프링 부트 활용 - 1) (0) 2020.03.09 Null-Safety (스프링 핵심 기술 - 6) (0) 2020.03.05 SpEL(Spring Expression Language) (스프링 핵심 기술 - 4) (0) 2020.03.05 데이터 바인딩 추상화 (스프링 핵심 기술 - 3) (0) 2020.03.04 Resource / Validation (스프링 핵심 기술 - 2) (0) 2020.03.04