Notice
Recent Posts
Recent Comments
Link
일 | 월 | 화 | 수 | 목 | 금 | 토 |
---|---|---|---|---|---|---|
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 |
Tags
- 자바ORM표준JPA프로그래밍
- 선형판별분석
- 이것이 MySQL이다
- bisection
- 인공지능
- 로지스틱 회귀
- 알고리즘대회
- 2018
- chapter01
- directed graphical model
- 5397번
- chapter02
- 델타 rule
- 근구하기
- 1차예선
- MySQL
- CH01
- undirected graphical model
- 개발순서
- 스터디
- Perceptron Convergence theorem
- Numerical optimization
- secant
- 알고리즘
- graphical models
- Fisher discriminant analysis
- 선형분류
- falsePosition
- vector미분
- SCPC
Archives
- Today
- Total
computer_study
[Spring] 07. AOP 프로그래밍 본문
목차
1. 프로젝트 준비
2. 프록시와 AOP
3. 스프링 AOP구현
4. 프록시 생성 방식
1. 프로젝트 준비
- AOP : Aspect Oriented Programming
- 스프링에선 spring-aop 모듈을 제공한다.
- spring-context, aspectjweaver 모듈을 추가하여 사용할 수 있다.
2. 프록시와 AOP
프록시
- 핵심 기능의 실행은 다른 객체에 위임하고 부가적인 기능을 제공하는 객체
- ex) a 연산을 진행하는데 걸리는 시간을 구하고 싶다면
시간을 구하는 객체에서 a연산을 호출만 한다. (직접 구현 x) - 여러 객체에 공통으로 적용할 수 있는 기능을 구현한다
AOP
- 핵심 기능과 공통 기능을 분리하는 것(재 사용성을 높여주는 프로그래밍 기법)
- 핵심 기능의 코드를 수정하지 않으면서 공통 기능의 구현을 추가하는 것
- 런타임에 프록시 객체를 생성해서 공통 기능을 삽입하는 방법이 사용된다(spring에서)
- 관련 용어
- Advice
- 언제 공통 기능을 핵심 로직에 적용할지 정의한다
- Before Advice
- 대상 객체의 메서드 호출 전 실행
- After Returning Advice
- 대상 객체의 메서드가 익셉션 없이 실행된 이후에 실행
- After Throwing Advice
- 대상 객체의 메서드 실행 도중 익셉션 발생한 경우 실행
- After Advice
- 익셉션에 상관 없이 대상 객체 메서드 실행 후 실행
- Around Advice
- 가장 널리 사용
- 대상 객체의 메서드 실행 전, 후 or 익셉션 발생 시점에 실행
- Aspect
- 공통으로 적용되는 기능
- JointPoint
- Advice를 적용 가능한 지점
- Pointcut
- 실제 Advice가 적용되는 Jointpoint
- Weaving
- Advice를 핵심 로직 코드에 적용하는 것
- Advice
3. 스프링 AOP구현
구현 방법
- Aspect로 사용할 클래스에 @Aspect 애노테이션 붙인다
- @Paintcut 애노테이션으로 공통 기능을 적용할 pointcut을 정의
- 공통 기능을 구현한 메서드에 @Around 애노테이션을 적용
@Aspect
public class ExeTimeAspect{
// 공통 기능을 적용 할 대상 설정
// chap07패키지와 그 하위 패키지에 위치한 타입의 public 메서드를 pointcut으로 설정한다는 의미
@Pointcut("execution(public*chap07..*(..))")
private void publicTarget(){
}
// Around Advice 설정
// publicTarget()메서드에 정의한 pointcut에 공통기능을 적용한다는 의미
// chap07 패키지나 그 하위 페키지에 속한 빈 객체의 public 메서드에 @Around가 붙은 measure()메서드 적용
@Around("publicTarget()")
public Object measure(ProceedingJoinPoint jointpoint) throws Throwable{
...
}
}
// AppCtx.java (스프링 설정클래스)
@Configuration
@EnableAspectJAutoProxy // @Aspect 애노테애션 클래스를 공통 기능으로 적용하기 위해(스프링이 찾는다)
public class AppCtx{
@Bean
public ExeTimeAspect exeTimeAspect(){
return new ExeTimeAspect();
}
@Bean
public Calculator calculator(){
return new RecCalculator();
}
}
ProceedingJoinPoint의 매서드
Around Advice에서 사용할 공통 기능 메서드를 활용하기 위해 proceed()메서드를 호출한다.
ProceedingJointPoint 인터페이스가 제공하는 메서드
- Signature getSignature()
- 호출되는 메서드에 대한 정보
- Object getTarget()
- 대상 객체 구하기
- Object[] getArgs()
- 파라미터 목록 구하기
org.aspectj.lang.Signature 인터페이스가 제공하는 메서드
- String getName()
- 호출되는 메서드 이름 구하기
- String toLongString()
- 호출되는 메서드를 완전하게 표현한 문장
- String toShortString()
- 호출되는 메서드를 축약해서 표현한 문장
4. 프록시 생성 방식
스프링은 AOP를 위한 프록시 객체를 생성할 때 실제 생성할 빈 객체가 인터페이스를 상속하면 인터페이스를 이용해서 프록시를 생성한다.
인터페이스가 아닌 클래스를 이용해 프록시를 생성하기 위해선 설정이 필요하다.
@Configuration
@EnableAspectJAutoProxy(proxyTargetClass = true)
public class AppCtx{
}
인터페이스 Calculator , 앞선 인터페이스를 상속받은 RecCalculator가 있다고할 때
Calculator cal = ctx.getBean("calculator", Calculator.class)
//위 코드를 아래처럼 변경할 수 있게 된다.
RecCalculator cal = ctx.getBean("calculator", RecCalculator.class)
//proxyTargetClass 을 true로 하지 않는다면, 생성된 프록시는 RecCalculator가 아닌 Calculator를 상속하기에 에러가 발생한다
execution 명시자 표현식
- 위 3번, pointcut 예시 참고
- Advice를 적용할 메서드를 지정할 때 사용
- 형식
- execution([수식어패턴] [리턴타입패턴] [클래스이름 패턴?메서드 이름 패턴(파라미터 패턴)])
- 수식어 패턴
- 생략 가능, public이 온다 (스프링 AOP에서)
- 클래스 이름 패턴, 메서드 이름 팬턴
- 클래스 이름 및 메서드 이름을 패턴으로 명시
- 파라미터 패턴
- 매칭될 파라미터에 대해 명시
- 명시자 예시
- '*'
- 모든 값을 표현 가능
- '..'
- 0개 이상임을 표현 가능
- '*'
Advice 적용 순서
@Order 애노테이션을 사용하여 적용 순서를 지정할 수 있다.
import org.springframework.core.annotation.Order;
@Aspect
@Order(1)
public class ExeTimeAspect{
}
@Aspect
@Order(2)
public class CacheAspect{
}
위와 같이 지정한다면, ExeTimeAspect 프록시 -> CacheAspect 프록시 -> 실제 대상 객체 순서로 지정된다.
@Around의 Pointcut 설정과 @Pointcut 재사용
- @Around 애노테이션에 execution 명시자를 지정할 수 있다.
- @Around("executiuon(public * chap07 ..*(..))")
- 같은 pointcut을 여러 Advice가 함께 사용한다면 공통 Pointcut을 재상용할 수도 있다
- 여러 Aspect에서 공통으로 사용하는 Pointcut이 있다면 별도 클래스에 Pointcut을 정의하고 Aspect클래스에서 해당 pointcut을 사용하도록 구성하면 관리가 편해진다
- 공통 Pointcut은 빈으로 등록할 필요 없이 @Around 애노테이션으로 사용할 수 있따.
'스터디 > 스프링5 프로그래밍 입문' 카테고리의 다른 글
[Spring] 09. 스프링 MVC 시작하기 (0) | 2022.04.27 |
---|---|
[Spring] 08. DB연동 (0) | 2022.04.24 |
[Spring] 06. 빈 라이프사이클과 범위 (0) | 2022.04.17 |
[Spring] 05. 컴포넌트 스캔 (0) | 2022.04.09 |
[Spring] 04. 의존 자동 주입 (0) | 2022.04.09 |
Comments