처음에 AOP라는 기능을 보았을 때 놀랐다. 개발하는 방향에 있어서 좋은 기능이라는 것 !
나름 쉽게 적어 놓았는데 어떨지 모르겠다.
AOP 란
- 비즈니스 로직에 영향을 주지 않고 사이사이에 공통 모듈을 효과적으로 잘 끼워 넣도록 하는 개발방법이다.
- 관점을 옆으로(?) 주고 공통 모듈을 끼워 넣도록 하는 개발 방법이다.
AOP 주요 구성요소
1. JoinPoint
- 모듈이 삽입되어 실행될 수 있는 특정 위치
- 제어 흐름중의 한 시점
2. PointCut
- 어떤 클래스의 어느 조인포인트를 사용할 지 선택하는 기능
3. Advice
- JointPoint에 삽입되어 동작할 수 있는 코드
- 동작시점
before : Matching 된 JoinPoint 이전에 동작하는 Advice
after returning : Matching 된 JoinPoint 이전에 동작하는 Advice
after throwing : Matching 된 JoinPoint Exception이 발생하여 종료된 후 동작하는 Advice
after : Matching 된 JoinPoint가 종료된후 동작하는 Advice
around : Matcing 된 JointPoint가 종료된 후 동작하는 Advice
4. Weaving
- Core Concerns 모듈에 Crosscutting Concerns 모듈 엮어서 동작수행
5. Aspect
- 어디에서 무엇을 할 것인지를 합쳐놓은것을 말함
예제)
- 인터셉터와 AOP를 이용한 Request 바인딩 코드
@Aspect
public class BindingAspect extends HandlerInterceptorAdapter {
protected Log log = LogFactory.getLog(BindingAspect.class);
static HttpServletRequest request;
@Override
public boolean preHandle(HttpServletRequest request, HttpServletResponse response, Object handler) throws Exception {
this.request = request;
System.out.println(request);
return super.preHandle(request, response, handler);
}
@Before("execution(* com.highluck.Service.*Service.*(..))")
public void binding(JoinPoint joinPoint) throws Throwable{
Object target = joinPoint.getTarget();
//HttpServletRequest requests = (HttpServletRequest)joinPoint.getArgs();
Field[] arrField = target.getClass().getFields();
if(request.getParameterNames() != null){
for (int i = 0; i < arrField.length; i++) {
Field field = arrField[i];
System.out.println(field.getType()+ " == " +int.class);
try {
if(field.getType() == int.class){
System.out.println("asdasd :" +request.getParameter(field.getName()));
field.set(joinPoint.getThis(), Integer.parseInt(request.getParameter(field.getName())));
} else if(field.getType() == double.class){
field.set(Target.class, Double.parseDouble(request.getParameter(field.getName())));
} else{
field.set(Target.class, request.getParameter(field.getName()));
}
log.debug(field);
} catch (IllegalArgumentException | IllegalAccessException e) {
e.printStackTrace();
} catch (NullPointerException e) {
continue;
}
}
}
request = null;
}
}
앞전에 리플렉션을 이용해서 만든 바인딩 코드를 AOP를 이용해서 만들었다.
여기서 사용 되었던 포인트컷 지시자에 대한 설명을 퍼온 내용이다.
AspectJ에서는 다섯 가지 종류의 Advice를 이용할 수 있는데 각각 @Before, @AfterReturning, @AfterThrowing, @After, @Around 어노테이션으로 표현된다.
이 코드는 @Around로 시작하기 때문에, Around Advice임을 알수 있다.
그 다음으로 "execution"은 포인트컷 표현식 부분이다.
포인트컷 표현식은 위에서 사용된 execution()을 포함하여 여러가지 포인트컷 지시자(PointCut Designator)를 사용할 수 있다.
그 종류는 다음과 같다.
execution() : 가장 대표적이고 강력한 지시자로, 접근제어자, 리턴 타입, 타입 패턴, 메서드, 파라미터 타입, 예외 타입 등을 조합해서 메서드까지 선택가능한 가장 정교한 포인트컷을 만들수 있다.
within() : 타입 패턴만을 이용하여 조인포인트를 정의한다.
this : 빈 오브텍트의 타입의 조인토인트를 정의한다.
target : 대상객체의 타입 비교를 이용한 조인포인트를 정의한다.
args : 메서드의 파라미터 타입만을 이용하여 조인포인트를 정의한다.
@target : 특정 어노테이션이 정의된 객체를 찾는 조인포인트를 정의한다.
@args : 특정 어노테이션을 파라미터로 받는 오브젝트를 찾는 조인포인트를 정의한다.
@within : @target과 유사하게 특정 어노테이션이 정의된 객체를 찾는데, 선택될 조인포인트 메서드는 타겟 클래스에서 선언이 되어있어야 한다.
@annotation : 조인 포인트 메서드에 특정 어노테이션을 찾는 조인포인트를 정의한다.
참고 : http://addio3305.tistory.com/32
'Programming > SpringFramework' 카테고리의 다른 글
나의 프레임워크 설계 ref 스프링 - 0 - (0) | 2016.04.29 |
---|---|
bean scope 명시 (0) | 2016.04.24 |
HTTP 에러정리 (0) | 2016.04.09 |
Spring DI & IOC (0) | 2016.04.01 |
Reflect API - 나만의 라이브러리 만들기 - (0) | 2016.02.10 |