๐Ÿ’ป cs

Spring | AOP์— ๋Œ€ํ•ด ์•Œ์•„๋ณด์ž !!

c0zi 2023. 7. 27. 15:07

1. AOP์˜ ์ •์˜ ๋ฐ ์›๋ฆฌ


AOP : ๊ด€์  ์ง€ํ–ฅ ํ”„๋กœ๊ทธ๋ž˜๋ฐ (Aspect Oriented Programming) 

- ๊ด€์  ์ง€ํ–ฅ์€ ์–ด๋–ค ๋กœ์ง์„ ๊ธฐ์ค€์œผ๋กœ ํ•ต์‹ฌ์ ์ธ ๊ด€์ , ๋ถ€๊ฐ€์ ์ธ ๊ด€์ ์œผ๋กœ ๋‚˜๋ˆ„์–ด์„œ ๋ณด๊ณ  ๊ทธ ๊ด€์ ์„ ๊ธฐ์ค€์œผ๋กœ ๋ชจ๋“ˆํ™”ํ•˜๋Š” ๊ฒƒ

 

ํ•ต์‹ฌ์ ์ธ ๊ด€์ ์€ ๋น„์ฆˆ๋‹ˆ์Šค ๋กœ์ง์œผ๋กœ ๋ณผ ์ˆ˜ ์žˆ๊ณ , ๋ถ€๊ฐ€์ ์ธ ๊ด€์ ์€ ํ•ต์‹ฌ ๋กœ์ง์„ ์‹คํ–‰ํ•˜๊ธฐ ์œ„ํ•ด ํ–‰ํ•ด์ง€๋Š” ๋ฐ์ดํ„ฐ๋ฒ ์ด์Šค ์—ฐ๊ฒฐ, ๋กœ๊น…, ํŒŒ์ผ ์ž…์ถœ๋ ฅ ๋“ฑ์ด ์žˆ๋‹ค.

 

AOP์—์„œ ๊ฐ ๊ด€์ ์„ ๊ธฐ์ค€์œผ๋กœ ๋กœ์ง์„ ๋ชจ๋“ˆํ™”ํ•œ๋‹ค๋Š” ๊ฒƒ์€ ์ฝ”๋“œ๋“ค์„ ๋ถ€๋ถ„์ ์œผ๋กœ ๋‚˜๋ˆ„์–ด์„œ ๋ชจ๋“ˆํ™”ํ•˜๊ฒ ๋‹ค๋Š” ์˜๋ฏธ์ด๋‹ค. ์ด๋•Œ, ์†Œ์Šค ์ฝ”๋“œ์ƒ์—์„œ ๋‹ค๋ฅธ ๋ถ€๋ถ„์— ๊ณ„์† ๋ฐ˜๋ณตํ•ด์„œ ์“ฐ๋Š” ์ฝ”๋“œ๋“ค์„ ๋ฐœ๊ฒฌํ•  ์ˆ˜ ์žˆ๋Š” ๋ฐ ์ด๊ฒƒ์„ ํฉ์–ด์ง„ ๊ด€์‹ฌ์‚ฌ (Crosscutting Concerns)๋ผ๊ณ  ํ•œ๋‹ค.

 

์ด์™€ ๊ฐ™์ด AOP๋ฅผ ์‚ฌ์šฉํ•˜๋ฉด ์ฝ”๋“œ์˜ ๊ฐ€๋…์„ฑ๊ณผ ์œ ์ง€ ๋ณด์ˆ˜์„ฑ์„ ๋†’์ผ ์ˆ˜ ์žˆ๋‹ค.

 

๐Ÿ“Œ AOP์˜ ์ดํ•ด๋ฅผ ๋•๊ธฐ ์œ„ํ•œ ์˜ˆ์‹œ

 

์˜ˆ๋ฅผ ๋“ค์–ด, ์ฒซ๋ฒˆ์งธ ๊ทธ๋ฆผ์—์„œ Class A, B, C์—๋Š” ๊ณตํ†ต์ ์ธ ๋‚ด์šฉ์ด ํฌํ•จ๋˜์–ด ์žˆ๋‹ค. ์ด๋Ÿฌํ•œ ๊ณตํ†ต์ ์ธ ๋‚ด์šฉ์„ ์ƒ‰๊น”๋กœ ๊ตฌ๋ถ„ํ•˜์—ฌ ํ‘œํ˜„ํ•˜์˜€์œผ๋ฉฐ, ์ด๋Ÿฌํ•œ ๊ณตํ†ต์ ์ธ ๋‚ด์šฉ์—๋Š” ๋ฉ”์„œ๋“œ๋‚˜ ํ•„๋“œ ๋“ฑ์ด ์žˆ๋‹ค. ๊ณตํ†ต์ ์ธ ๋ถ€๋ถ„์ด ๋‹ค๋ฅธ ํด๋ž˜์Šค๋“ค ๋‚ด๋ถ€์— ์กด์žฌํ•œ๋‹ค๋ฉด, ๊ฐ™์€ ๋ธ”๋ก์„ ์ˆ˜์ •ํ•˜๋Š”๋ฐ ์—ฌ๋Ÿฌ ํด๋ž˜์Šค์˜ ๋ธ”๋ก๋“ค์„ ๋”ฐ๋กœ ์ˆ˜์ •ํ•ด์•ผ ํ•˜๋Š” ์ƒํ™ฉ์ด ๋ฐœ์ƒํ•œ๋‹ค.

 

์ด์™€ ๊ฐ™์€ ๋ฌธ์ œ๋Š” SOLID์›์น™์„ ์œ„๋ฐฐํ•˜๋ฉฐ ์œ ์ง€๋ณด์ˆ˜๋ฅผ ์–ด๋ ต๊ฒŒ ๋งŒ๋“ ๋‹ค. ์ด๋•Œ์˜ ์ฃผํ™ฉ, ํŒŒ๋ž‘, ๋นจ๊ฐ• ๋ธ”๋ก์„ ํฉ์–ด์ง„ ๊ด€์‹ฌ์‚ฌ(Crosscutting Concerns)๋ผ๊ณ  ํ•œ๋‹ค. ์ด๋Ÿฌํ•œ ํฉ์–ด์ง„ ๊ด€์‹ฌ์‚ฌ๋“ค์„ ๋ชจ๋“ˆํ™”ํ•˜๊ณ  ํ•ด๋‹น ๊ธฐ๋Šฅ์ด ํ•„์š”ํ•œ ๋ธ”๋Ÿญ์— ์ ์šฉํ•ด์ฃผ๋Š” ๊ฒƒ์ด AOP์˜ ์›๋ฆฌ์ด๋‹ค. ์ด๋•Œ, ๋ชจ๋“ˆํ™” ์‹œ์ผœ๋†“์€ ๋ธ”๋Ÿญ์„ Aspect๋ผ๊ณ  ํ•œ๋‹ค. 

 

๋‘๋ฒˆ์งธ ๊ทธ๋ฆผ์—์„œ ๊ณ„์ขŒ์ด์ฒด, ๋Œ€์ถœ์Šน์ธ, ์ด์ž๊ณ„์‚ฐ ๋“ฑ์€ ํ•ต์‹ฌ๋กœ์ง์— ํ•ด๋‹น๋œ๋‹ค๊ณ  ๋ณผ ์ˆ˜ ์žˆ๊ณ , ๋กœ๊น…์ด๋‚˜ ๋ณด์•ˆ, ํŠธ๋žœ์žญ์…˜ ๋“ฑ์˜ ๊ณตํ†ต๋˜๋Š” ๊ธฐ๋Šฅ๋“ค์€ ๋ถ€๊ฐ€ ๊ธฐ๋Šฅ์ด๋ผ๊ณ  ๋ณผ ์ˆ˜ ์žˆ๋‹ค. 

 


2. AOP ์šฉ์–ด ์ •๋ฆฌ


1) Advice: ๋ถ€๊ฐ€๊ธฐ๋Šฅ์„ ์ˆ˜ํ–‰ํ•  ๋ฉ”์„œ๋“œ ์ƒ์„ฑ

2) Pointcut: ๋ถ€๊ฐ€ ๊ธฐ๋Šฅ์„ ์ ์šฉํ•  ํ•ต์‹ฌ๋กœ์ง์„ ๊ฒฐ์ •ํ•ฉ๋‹ˆ๋‹ค.

3) Aspect: ๋ถ€๊ฐ€ ๊ธฐ๋Šฅ๊ณผ ํ•ด๋‹น ๋ถ€๊ฐ€ ๊ธฐ๋Šฅ์„ ์–ด๋””์— ์ ์šฉํ• ์ง€ ์ •์˜ํ•œ ๊ฒƒ์ž…๋‹ˆ๋‹ค. (ํด๋ž˜์Šค ์ƒ์„ฑ Advice + Pointcut)

4) Joinpoint : ๋ถ€๊ฐ€๊ธฐ๋Šฅ์ด ํ•ต์‹ฌ๋กœ์ง ์‹คํ–‰์ „์— ์‹คํ–‰๋ ์ง€ ํ›„์— ์‹คํ–‰๋ ์ง€๋ฅผ ๊ฒฐ์ •ํ•ฉ๋‹ˆ๋‹ค.

 

[ex] ๋กœ๊ทธ์ธ ๋ฉ”์„œ๋“œ๊ฐ€ ์žˆ๋‹ค. ๋ฉ”์„œ๋“œ์˜ ์ด๋ฆ„์€ login() ์ด๊ณ  ์ด ๋ฉ”์„œ๋“œ๋Š” ํ•ต์‹ฌ๋กœ์ง์ด๋‹ค. ๋กœ๊ทธ์ธ ๋ฉ”์„œ๋“œ๊ฐ€ ์‹คํ–‰๋  ๋•Œ ๋งˆ๋‹ค ๋กœ๊ทธ๋ฅผ ๋‚จ๊ธฐ๊ณ  ์‹ถ๋‹ค๋ฉด (>> ๋ถ€๊ฐ€๊ธฐ๋Šฅ), ๋กœ๊ทธ๋ฅผ ๋‚จ๊ธธ ๋ฉ”์„œ๋“œ๋ฅผ ๋งŒ๋“ค์–ด์•ผ ํ•œ๋‹ค. ์ด๊ฒƒ์„ ๋ถ€๊ฐ€๋กœ์ง์ด๋ผ๊ณ  ํ•œ๋‹ค. 

 

๐Ÿ–ฅ๏ธ ํ•ต์‹ฌ๋กœ์ง, ๋ถ€๊ฐ€๋กœ์ง

login(){} // ํ•ต์‹ฌ๋กœ์ง

log(){ // ๋ถ€๊ฐ€๋กœ์ง
	System.out.println("๋กœ๊ทธ ์‹คํ–‰๋จ");
}

 

์ด์ œ ๋ถ€๊ฐ€๋กœ์ง์— pointcut์„ ์ ์šฉํ•˜์—ฌ login() ๋ฉ”์„œ๋“œ๊ฐ€ ์‹คํ–‰๋ ๋•Œ๋งˆ๋‹ค ๋ฐœ๋™ํ•˜๊ฒŒ ํ•œ๋‹ค.

 

pointcut(login()) // point cut : ๋ถ€๊ฐ€๋กœ์ง ์‹คํ–‰ํ•  ํ•ต์‹ฌ๋กœ์ง ๊ฒฐ์ •
log(){
	System.out.println("๋กœ๊ทธ ์‹คํ–‰๋จ");
}

 

๋งˆ์ง€๋ง‰์œผ๋กœ joinpoint๋ฅผ ํ†ตํ•ด์„œ ์–ธ์ œ ์‹คํ–‰๋ ์ง€ ๊ฒฐ์ •ํ•œ๋‹ค.

 

Before // join point : ํ•ต์‹ฌ ๋กœ์ง ์ „ or ํ›„ ๊ฒฐ์ •
pointcut(login())
log(){
	System.out.println("๋กœ๊ทธ ์‹คํ–‰๋จ");
}

 

์œ„ ๋ฐฉ์‹์œผ๋กœ ์ž‘์„ฑํ•˜๊ฒŒ ๋˜๋ฉด join() ๋ฉ”์„œ๋“œ๊ฐ€ ์‹คํ–‰๋ ๋•Œ ๋กœ๊ทธ๋ฅผ ๋‚จ๊ธธ์ˆ˜๋Š” ์—†๋‹ค. ๊ทธ๋ž˜์„œ ์–ด๋…ธํ…Œ์ด์…˜์„ ๋งŒ๋“œ๋Š” ๊ฒƒ์ด ์ข‹๋‹ค. ์•„๋ž˜์™€ ๊ฐ™์ด ์ ์šฉํ•˜๋ฉด @MyLog ์–ด๋…ธํ…Œ์ด์…˜์ด ๋ถ™์–ด์žˆ์œผ๋ฉด ๋กœ๊ทธ๊ฐ€ ์‹คํ–‰ํ•œ๋‹ค.

 

@MyLog
login(){} // login ๋ฉ”์„œ๋“œ๊ฐ€ ์‹คํ–‰๋  ๋•Œ

@MyLog
join(){} // join ๋ฉ”์„œ๋“œ๊ฐ€ ์‹คํ–‰๋  ๋•Œ
After
pointcut(@MyLog)
log(){
	System.out.println("๋กœ๊ทธ ์‹คํ–‰๋จ");
}

 


3. AOP ์ ์šฉ๋ฐฉ๋ฒ• 3๊ฐ€์ง€


1) ์ฒซ๋ฒˆ์งธ ๋ฐฉ๋ฒ• - ์–ด๋…ธํ…Œ์ด์…˜ ์ƒ์„ฑ

 

  • ์–ด๋…ธํ…Œ์ด์…˜์„ ๋งŒ๋“ค๊ณ  ๊ทธ ์—๋„ˆํ…Œ์ด์…˜์„ PointCut์œผ๋กœ ๋“ฑ๋กํ•œ๋‹ค.
  • Advice๋ฅผ ๋งŒ๋“ ๋‹ค. (๋ฉ”์„œ๋“œ ํ–‰์œ„)
  • JoinPoint๋ฅผ ์ ์šฉํ•œ๋‹ค

 

์œ„์˜ ์˜ˆ์‹œ์—์„œ ์„ค๋ช…ํ•œ ๋ฐฉ๋ฒ•๊ณผ ๊ฐ™๋‹ค.

 

@Target(ElementType.METHOD) // method์— ๋ถ€์ฐฉ๊ฐ€๋Šฅ
@Retention(RetentionPolicy.RUNTIME) // ๋Ÿฐํƒ€์ž„ ์‹œ์ ๊นŒ์ง€ ์–ด๋…ธํ…Œ์ด์…˜์˜ ๋ฉ”๋ชจ๋ฆฌ๋ฅผ ๊ฐ€์ ธ๊ฐ
public @interface Hello {
}
@Aspect
@Component
public class HelloAdvice {

    // ํฌ์ธํŠธ ์ปท์„ ์–ด๋…ธํ…Œ์ด์…˜์— ์ ์šฉ
    @Pointcut("@annotation(Hello)")
    public void hello(){}
    
    // JoinPoint ์ ์šฉ
    @Before("hello()")
    public void helloAdvice(JoinPoint jp) throws Throwable {
        Object[] args = jp.getArgs();
        
        if(args.length < 1){
            System.out.println("์•„๋ฌด๊ฐœ๋‹˜ ์•ˆ๋…•");
        }
        else{
            for (Object arg : args) {
                if(arg instanceof String){
                    String username = (String) arg;
                    System.out.println(username+"๋‹˜ ์•ˆ๋…•");
                }
            }
        }
        
    }
}

 

2) ๋‘๋ฒˆ์งธ ๋ฐฉ๋ฒ• - PointCut๋งŒ ๋“ฑ๋ก

 

  • ์ด๋ฏธ ๋งŒ๋“ค์–ด์ ธ ์žˆ๋Š” ์–ด๋…ธํ…Œ์ด์…˜์— PointCut ๋“ฑ๋ก ํ•œ๋‹ค.
  • Advice๋ฅผ ๋งŒ๋“ ๋‹ค. (๋ฉ”์„œ๋“œ ํ–‰์œ„)
  • JoinPoint๋ฅผ ์ ์šฉํ•œ๋‹ค 

 

@Aspect
@Component
public class ValidAdvice {

    @Pointcut("@annotation(org.springframework.web.bind.annotation.PostMapping)")
    public void postMapping() {}
    
    @Pointcut("@annotation(org.springframework.web.bind.annotation.PutMapping)")
    public void putMapping() {}
    
    @Before("postMapping() || putMapping()")
    public void validationAdvice(JoinPoint jp) throws Throwable {
    
        Object[] args = jp.getArgs();
        
        for (Object arg : args) {
        
            if (arg instanceof BindingResult) {
                Errors errors = (Errors) arg;
                
                    if (errors.hasErrors()) {
                    Map<String, String> errorMap = new HashMap<>();
                    
                    for (FieldError error : errors.getFieldErrors()) {
                        errorMap.put(error.getField(),
                        error.getDefaultMessage());
                    }
                    
                throw new MyValidationException(errorMap);
                
                }
            }
        }
    }
}

 

3) ์„ธ๋ฒˆ์งธ ๋ฐฉ๋ฒ• - ์—๋„ˆํ…Œ์ด์…˜ x, ํŠน์ • ํŒจํ„ด

 

๊นƒ๋ฐœ์„ ์ƒ์„ฑํ•˜์ง€ ์•Š๊ณ , ํŠน์ •ํ•œ ํŒจํ„ด์ด ์ˆ˜ํ–‰๋  ๋•Œ ์ •์˜๋œ advice๋ฅผ ์‹คํ–‰ํ•˜๊ฒŒ ํ•  ์ˆ˜๋„ ์žˆ๋‹ค.

 

Spring Framework์—์„œ๋Š” XML์„ ์ด์šฉํ•˜์—ฌ Aspect-Oriented Programming (AOP)์„ ์„ค์ •ํ•˜๋Š” ๋ฐฉ๋ฒ•์ด ์žˆ๋‹ค.

๊ทธ๋Ÿฌ๋‚˜ Spring Boot์—์„œ๋Š” ์ฃผ๋กœ ์–ด๋…ธํ…Œ์ด์…˜ ๊ธฐ๋ฐ˜์˜ AOP๋ฅผ ์‚ฌ์šฉํ•˜๋ฉฐ, execution expression์„ ์ด์šฉํ•˜์—ฌ pointcut์„ ๋“ฑ๋กํ•  ์ˆ˜ ์žˆ๋‹ค.

 

ํ•˜์ง€๋งŒ, ์ง์ ‘์ ์œผ๋กœ execution expression์„ ์ด์šฉํ•˜์—ฌ pointcut์„ ๋“ฑ๋กํ•˜๋ ค๋ฉด ์—ฌ๋Ÿฌ๊ฐ€์ง€ ์„ค์ •์„ ํ•ด ์ฃผ์–ด์•ผ ํ•œ๋‹ค. ๋Œ€์‹ , Spring Boot์—์„œ๋Š” AspectJ๋ฅผ ์‚ฌ์šฉํ•˜์—ฌ ๊ฐ„ํŽธํ•˜๊ฒŒ pointcut์„ ๋“ฑ๋กํ•  ์ˆ˜ ์žˆ๋Š” ๊ธฐ๋Šฅ์„ ์ œ๊ณตํ•œ๋‹ค.

 

AspectJ๋Š” Java์™€ ๋น„์Šทํ•œ ๋ฌธ๋ฒ•์„ ๊ฐ€์ง€๋ฉฐ, execution expression์„ ์ด์šฉํ•˜์—ฌ pointcut์„ ๋“ฑ๋กํ•˜๋Š” ๋ฐฉ๋ฒ•์ด ์žˆ๋‹ค.

 

Execution Expression Point Cut
execution(* onj.spring.aop..(..)) ํŒจํ‚ค์ง€์˜ ๋ชจ๋“  ๋ฉ”์†Œ๋“œ๊ฐ€ ํฌ์ธํŠธ ์ปท
execution(* onj.spring.aop...(..)) onj.spring.aop ํŒจํ‚ค์ง€์™€ ํ•˜์œ„ ํŒจํ‚ค์ง€์˜ ๋ชจ๋“  ๋ฉ”์†Œ๋“œ๊ฐ€ ํฌ์ธํŠธ ์ปท
execution(public void insert*(..)) public์— ๋ฆฌํ„ด๊ฐ’, ํŒจํ‚ค์ง€๋ช… ์—†๊ณ  ๋ฉ”์„œ๋“œ ์ด๋ฆ„์€ insert๋กœ ์‹œ์ž‘,
์ธ์ž๊ฐ’์€ 0๊ฐœ ์ด์ƒ์ธ ๋ฉ”์„œ๋“œ๊ฐ€ ํฌ์ธํŠธ ์ปท
execution(public * *(..)) public ๋ฉ”์†Œ๋“œ๊ฐ€ ํฌ์ธํŠธ ์ปท
execution(* onj.spring.aop..()) ๋ฆฌํ„ดํ˜• ๊ด€๊ณ„์—†๊ณ  onj.spring.aop ํŒจํ‚ค์ง€์˜ ๋ชจ๋“  ํด๋ž˜์Šค,
์ธ์ž๊ฐ’์ด ์—†๋Š” ๋ชจ๋“  ๋ฉ”์„œ๋“œ๊ฐ€ ํฌ์ธํŠธ ์ปท
execution(* onj.spring.aop...(..)) ๋ฆฌํ„ดํ˜• ๊ด€๊ณ„์—†๊ณ  onj.spring.aop ํŒจํ‚ค์ง€ ๋ฐ ํ•˜์œ„ ํŒจํ‚ค์ง€์— ์žˆ๋Š” ๋ชจ๋“  ํด๋ž˜์Šค,
์ธ์ž๊ฐ’์ด 0๊ฐœ ์ด์ƒ์ธ ๋ฉ”์„œ๋“œ๊ฐ€ ํฌ์ธํŠธ ์ปท
execution(* delete()) ๋ฉ”์„œ๋“œ ์ด๋ฆ„์ด delete์œผ๋กœ ์‹œ์ž‘ํ•˜๋Š” ์ธ์ž๊ฐ’์ด 1๊ฐœ์ธ ๋ฉ”์„œ๋“œ๊ฐ€ ํฌ์ธํŠธ ์ปท
execution(* delete(,*)) ๋ฉ”์„œ๋“œ ์ด๋ฆ„์ด delete๋กœ ์‹œ์ž‘ํ•˜๋Š” ์ธ์ž๊ฐ’์ด 2๊ฐœ์ธ ๋ฉ”์„œ๋“œ๊ฐ€ ํฌ์ธํŠธ ์ปท

 

ํŠน์ • ์–ด๋…ธํ…Œ์ด์…˜์˜ ํŒŒ๋ผ๋ฏธํ„ฐ๋กœ ์žˆ๋Š” ๋ฉ”์†Œ๋“œ๋ฅผ pointcut์œผ๋กœ ์žก์œผ๋ ค๋ฉด, execution expression์„ ์ด์šฉํ•˜์—ฌ ์–ด๋…ธํ…Œ์ด์…˜์ด ์ ์šฉ๋œ ๋ฉ”์†Œ๋“œ๋ฅผ ๋Œ€์ƒ์œผ๋กœ pointcut์„ ์ž‘์„ฑํ•œ๋‹ค. ๋‹ค๋งŒ, ์ด ๊ฒฝ์šฐ์—๋Š” @annotation ๋Œ€์‹ ์— @args ํ‚ค์›Œ๋“œ๋ฅผ ์‚ฌ์šฉํ•ด์•ผ ํ•œ๋‹ค.

 


4. @Before, @After, @Around


AOP์—์„œ Before, After, Around๋Š” ๊ฐ๊ฐ ๋‹ค๋ฅธ ์‹œ์ ์—์„œ AOP ์–ด๋“œ๋ฐ”์ด์Šค๋ฅผ ์‹คํ–‰ํ•˜๋Š” ๋ฐฉ๋ฒ•์ด๋‹ค.

 

1. @Before

: ๋ฉ”์„œ๋“œ ์‹คํ–‰ ์ „์— ์–ด๋“œ๋ฐ”์ด์Šค๋ฅผ ์‹คํ–‰ํ•œ๋‹ค. ์ด ์‹œ์ ์—์„œ JoinPoint ๊ฐ์ฒด๋ฅผ ํ†ตํ•ด ๋ฉ” ์„œ๋“œ์˜ ์ธ์ž, ํด๋ž˜์Šค, ๋ฉ”์„œ๋“œ ์ด๋ฆ„ ๋“ฑ์˜ ์ •๋ณด๋ฅผ ๊ฐ€์ ธ์˜ฌ ์ˆ˜ ์žˆ๋‹ค. @Before ์–ด๋…ธํ…Œ์ด์…˜์„ ์‚ฌ์šฉํ•˜์—ฌ ์„ ์–ธํ•œ๋‹ค.

 

@Before("execution(* com.example.myapp.service.MyService.*(..))")
public void beforeAdvice(JoinPoint joinPoint) {
	System.out.println("Before Advice: " + joinPoint.getSignature().getName());
}

 

@Before ์–ด๋…ธํ…Œ์ด์…˜์„ ์‚ฌ์šฉํ•˜์—ฌ com.example.myapp.service.MyService ํด๋ž˜์Šค์˜ ๋ชจ๋“  ๋ฉ”์„œ๋“œ์— ์ ์šฉ๋  ์–ด๋“œ๋ฐ”์ด์Šค๋ฅผ ์ž‘์„ฑํ•œ๋‹ค. ๋ฉ”์„œ๋“œ ์‹คํ–‰ ์ „์— ํ•ด๋‹น ๋ฉ”์„œ๋“œ์˜ ์‹œ๊ทธ๋‹ˆ์ฒ˜ ์ •๋ณด๋ฅผ ์ถœ๋ ฅํ•˜๋Š” ๊ธฐ๋Šฅ์„ ์ˆ˜ํ–‰ํ•œ๋‹ค.

 

2. @After

: ๋ฉ”์„œ๋“œ ์‹คํ–‰ ํ›„์— ์–ด๋“œ๋ฐ”์ด์Šค๋ฅผ ์‹คํ–‰. ์ด ์‹œ์ ์—์„œ JoinPoint ๊ฐ์ฒด๋ฅผ ์‚ฌ์šฉํ•  ์ˆ˜ ์žˆ์œผ๋ฉฐ, ๋ฉ”์„œ๋“œ์˜ ์‹คํ–‰ ๊ฒฐ๊ณผ๋‚˜ ์˜ˆ์™ธ ์ •๋ณด ๋“ฑ์„ ๊ฐ€์ ธ์˜ฌ ์ˆ˜ ์žˆ๋‹ค. @After ์–ด๋…ธํ…Œ์ด์…˜์„ ์‚ฌ์šฉํ•˜์—ฌ ์„ ์–ธํ•œ๋‹ค.

 

@After("execution(* com.example.myapp.service.MyService.*(..))")
public void afterAdvice(JoinPoint joinPoint) {
	System.out.println("After Advice: " + joinPoint.getSignature().getName());
}

 

@After ์–ด๋…ธํ…Œ์ด์…˜์„ ์‚ฌ์šฉํ•˜์—ฌ com.example.myapp.service.MyService ํด๋ž˜์Šค์˜ ๋ชจ๋“  ๋ฉ”์„œ๋“œ์— ์ ์šฉ๋  ์–ด๋“œ๋ฐ”์ด์Šค๋ฅผ ์ž‘์„ฑํ•œ๋‹ค. ๋ฉ”์„œ๋“œ ์‹คํ–‰ ํ›„ ํ•ด๋‹น ๋ฉ”์„œ๋“œ์˜ ์‹œ๊ทธ๋‹ˆ์ฒ˜ ์ •๋ณด๋ฅผ ์ถœ๋ ฅ ํ•˜๋Š” ๊ธฐ๋Šฅ์„ ์ˆ˜ํ–‰ํ•ฉ๋‹ˆ๋‹ค.

 

3. @Around

: ๋ฉ”์„œ๋“œ ์‹คํ–‰ ์ „ํ›„ ๋ชจ๋‘ ์–ด๋“œ๋ฐ”์ด์Šค๋ฅผ ์‹คํ–‰ํ•œ๋‹ค. ์ด ์‹œ์ ์—์„œ ProceedingJoinPoint ๊ฐ์ฒด๋ฅผ ์‚ฌ์šฉํ•˜์—ฌ ๋ฉ”์„œ๋“œ ์‹คํ–‰์„ ์ˆ˜ํ–‰ํ•˜๊ณ , ์‹คํ–‰ ๊ฒฐ๊ณผ๋ฅผ ๋ฐ˜ํ™˜ํ•  ์ˆ˜ ์žˆ๋‹ค. @Around ์–ด๋…ธํ…Œ์ด์…˜์„ ์‚ฌ์šฉํ•˜์—ฌ ์„ ์–ธํ•˜๋ฉฐ, ๋ฉ”์„œ๋“œ ์‹คํ–‰ ์ „ํ›„์— ์ถ”๊ฐ€์ ์ธ ๋กœ์ง์„ ์ˆ˜ํ–‰ ํ•  ์ˆ˜ ์žˆ๋‹ค.

 

@Around("execution(* com.example.myapp.service.MyService.*(..))")
public Object aroundAdvice(ProceedingJoinPoint joinPoint) throws Throwable {
    System.out.println("Before Advice: " + joinPoint.getSignature().getName());
    Object result = joinPoint.proceed();
    System.out.println("After Advice: " + joinPoint.getSignature().getName());
    return result;
}

 

@Around ์–ด๋…ธํ…Œ์ด์…˜์„ ์‚ฌ์šฉํ•˜์—ฌ com.example.myapp.service.MyService ํด๋ž˜์Šค ์˜ ๋ชจ๋“  ๋ฉ”์„œ๋“œ์— ์ ์šฉ๋  ์–ด๋“œ๋ฐ”์ด์Šค๋ฅผ ์ž‘์„ฑํ•œ๋‹ค. ๋ฉ”์„œ๋“œ ์‹คํ–‰ ์ „ํ›„์— ํ•ด๋‹น ๋ฉ”์„œ๋“œ์˜ ์‹œ๊ทธ๋‹ˆ์ฒ˜ ์ •๋ณด๋ฅผ ์ถœ๋ ฅํ•˜๊ณ , ๋ฉ”์„œ๋“œ ์‹คํ–‰์„ ์ˆ˜ํ–‰ํ•œ ํ›„ ์‹คํ–‰ ๊ฒฐ๊ณผ๋ฅผ ๋ฐ˜ํ™˜ํ•ฉ๋‹ˆ๋‹ค.

 


์ฆ‰, @Before ๋Š” ๋ฉ”์„œ๋“œ ์‹คํ–‰ ์ „์— ์ถ”๊ฐ€์ ์ธ ๋กœ์ง์„ ์ˆ˜ํ–‰ํ•˜๋Š” ์–ด๋“œ๋ฐ”์ด์Šค์ด๊ณ  @After ๋Š” ๋ฉ”์„œ๋“œ ์‹คํ–‰ ํ›„์— ์ถ”๊ฐ€์ ์ธ ๋กœ์ง์„ ์ˆ˜ํ–‰ํ•˜๋Š” ์–ด๋“œ๋ฐ”์ด์Šค์ด๋‹ค. @Around ๋Š” ๋ฉ”์„œ๋“œ ์‹คํ–‰ ์ „ํ›„์— ์ถ”๊ฐ€์ ์ธ ๋กœ์ง์„ ์ˆ˜ํ–‰ํ•  ์ˆ˜ ์žˆ๋Š” ๊ฐ€์žฅ ๋ฒ”์šฉ์ ์ธ ์–ด๋“œ๋ฐ”์ด์Šค์— ํ•ด๋‹นํ•œ๋‹ค.

 

AOP์—์„œ ๋ฉ”์„œ๋“œ์˜ ํŒŒ๋ผ๋ฏธํ„ฐ ๊ฐ’์„ ๊ฒ€์‚ฌํ•˜๊ฑฐ๋‚˜ ๋ณ€๊ฒฝํ•˜๋Š” ์ž‘์—…์„ ์ˆ˜ํ–‰ํ•  ๋•Œ๋Š” @Before ์–ด๋…ธํ…Œ์ด์…˜์„ ์‚ฌ์šฉํ•˜๊ณ , ๋ฉ”์„œ๋“œ ์‹คํ–‰ ์‹œ์— ์ƒˆ๋กœ์šด ๊ฐ’์„ ์ฃผ์ž…ํ•˜๊ฑฐ๋‚˜, ๊ฒฐ๊ณผ๋ฅผ ๊ฐ€๊ณตํ•˜๋Š” ์ž‘์—…์„ ์ˆ˜ํ–‰ํ•  ๋•Œ๋Š” @Around ์–ด๋…ธํ…Œ์ด์…˜์„ ์‚ฌ์šฉํ•˜๋Š” ๊ฒƒ์ด ์ผ๋ฐ˜์ ์ด๋‹ค

 


์ฐธ๊ณ ์ž๋ฃŒ


1. https://code-lab1.tistory.com/193

 

[Spring] AOP(Aspect Oriented Programming)๋ž€? ์Šคํ”„๋ง AOP๋ž€?

AOP (Aspect Oriented Programming)๋ž€? AOP๋Š” Aspect Oriented Programming์˜ ์•ฝ์ž๋กœ ๊ด€์  ์ง€ํ–ฅ ํ”„๋กœ๊ทธ๋ž˜๋ฐ์ด๋ผ๊ณ  ๋ถˆ๋ฆฐ๋‹ค. ๊ด€์  ์ง€ํ–ฅ์€ ์–ด๋–ค ๋กœ์ง์„ ๊ธฐ์ค€์œผ๋กœ ํ•ต์‹ฌ์ ์ธ ๊ด€์ , ๋ถ€๊ฐ€์ ์ธ ๊ด€์ ์œผ๋กœ ๋‚˜๋ˆ„์–ด์„œ ๋ณด๊ณ  ๊ทธ

code-lab1.tistory.com

2. https://engkimbs.tistory.com/746

 

[Spring] ์Šคํ”„๋ง AOP (Spring AOP) ์ด์ •๋ฆฌ : ๊ฐœ๋…, ํ”„๋ก์‹œ ๊ธฐ๋ฐ˜ AOP, @AOP

| ์Šคํ”„๋ง AOP ( Aspect Oriented Programming ) AOP๋Š” Aspect Oriented Programming์˜ ์•ฝ์ž๋กœ ๊ด€์  ์ง€ํ–ฅ ํ”„๋กœ๊ทธ๋ž˜๋ฐ์ด๋ผ๊ณ  ๋ถˆ๋ฆฐ๋‹ค. ๊ด€์  ์ง€ํ–ฅ์€ ์‰ฝ๊ฒŒ ๋งํ•ด ์–ด๋–ค ๋กœ์ง์„ ๊ธฐ์ค€์œผ๋กœ ํ•ต์‹ฌ์ ์ธ ๊ด€์ , ๋ถ€๊ฐ€์ ์ธ ๊ด€์ ์œผ๋กœ

engkimbs.tistory.com