사용자가 만들어 사용하는 Custom Annotation은 어떻게 효과적으로 응용할 수 있는지 궁금할 것이다.
인터넷에 예제도 별로 없고..
내가 짠 것은 아니지만, Spring 프렘웍의 AOP를 이용해서 만든 커스텀 어노테이션 사용법에 대해서 정리하겠다
* AOP(Aspect Oriented Programming)이란?
먼저, OOP(Object Oriented Programming)의 경우, 객체 단위로 기능을 묶어서 코딩하는 방법이다.
그러나 실무에서는 이런 구현방법이 단점이 될 수 있다.
사용자 인증을 항상 해야 한다고 하면, 객체마다 반복되는 코드가 생기게 될 것이다.
그래서 사용자 인증 같이 자주 사용되는 코드를 단위로 묶어서 필요할 때마다 삽입하여 사용하는 것을 AOP 라고 한다.
사용자 인증하는 코드가 A라고 하고, 비지니스 부분을 B라고 한다면
[B가 실행되기 전 또는 후에 A를 실행한다.]
전체적으로는 위의 코드가 한 비지니스 로직에서 실행되는 것처럼 하는 것이다.
컨트롤러 타기전에 사용자 인증 하는 예제이다.
(1) 커스텀 어노테이션 설정
1. 어노테이션 인터페이스 작성
@Retention(RetentionPolicy.RUNTIME)
@Target(ElementType.Method)
public @interface PreAuth {
// Auth는 enum 임
Auth hasAuth() default com.x.x.Auth.VISITOR; // 어노테이션 속에 값이 없다면 디폴트로 VISITOR로 지정
}
*******************************************
@Retention : 어노테이션은 주석이기 때문에 컴파일시 사라진다. 하지만 retention을 통해, 런타임때까지 주석을 남기겠다 라고 컴파일러에게 알려줌
@Target : 어디에 어노테이션을 적용할 지 타겟을 정함
retention에도 옵션이 많고, 이 어노테이션들 말고 옵션이 더 있지만 그건 찾아보면 나온당ㅋㅋ
2. Auth enum 구현
public enum Auth {
ADMIN(1), OWNER(2), USER(3), VISITER(4);
// 생략
}
*********************************************
숫자로 처리하기 위해 enum 사용.
3. 비지니스에서의 어노테이션 사용
@Controller
public class Text {
@PreAuth(hasAuth=Auth.OWNER)
public void view() {
// 비지니스 구현
}
}
(2) AOP
1. AOP 사용을 위한 xml 설정 (*-context.xml)
....
<aop:aspectj-autoproxy />
**********************************************
저 설정을 등록하면 @Aspect 어노테이션을 사용할 수 있다.
2. 인증 처리 구현
@Component
public class AuthManager {
// 인증 처리 구현
}
3. (2)2번에서 구현한 로직을 (1)3 에 삽입할 시점 구현(Aspect)
@Aspect
@Component
public class AuthAspect {
@Resource(name = "authManager")
AuthManager authManager;
@Pointcut("@annotation(com.x.x.annotation.PreAuth)") // @PreAuth가 있는 지점을 pointcut으로 지정
public void pointcut() { }
@Before("pointcut()") // pointcut 한 부분 이전에, 인증 수행(joinpoint)
public void beforeTargetMethod(JoinPoint joinPoint) {
hasAuth(joinPoint);
}
private void hasAuth(JoinPoint joinPoint) {
// Todo: reflection을 이용하여 어노테이션 속에 있는 값을 가져온다
authManager.hasAuth(hasRole); // 위에서 받아온 값을 넘긴다.
}
}
**********************************************
joinPoint : 메소드 호출 전/후 등의 적용 지점
pointcut : 실제 로직에 적용되는 joinpoint
※ 잘못 설명한게 있으면 지적 부탁드림
최근 덧글