[Spring] Spring의 특징 - AOP (관심 지향 프로그래밍)

전윤혁·2024년 7월 2일
0

Spring

목록 보기
4/8

Spring의 특징

  1. POJO (Plain Old Java Object)
    순수 Java 생성 객체 지향
  1. IoC / DI (Inversion of Control / Dependency Injection)
    제어의 역전 / 의존성 주입
  1. AOP (Aspect Oriented Programming)
    관심 지향 프로그래밍
  1. PSA (Portable Service Abstraction)
    일관된 서비스 추상화

AOP (Aspect Oriented Programming)

https://velog.io/@airoca/Spring-SpringSpring-Boot

AOP(Aspect-Oriented Programming, 관점 지향 프로그래밍)는 애플리케이션의 핵심 기능(Core Concern)공통적인 기능(Cross-cutting Concern)을 분리하여, 각각의 관점을 기준으로 개발을 진행하는 방식을 의미한다.

예를 들어, 고객 정보를 저장하고 조회하는 비즈니스 로직을 구현하려고 할 때, 핵심 기능은

1. 고객의 정보를 데이터베이스에 저장
2. 고객의 정보를 조회

두 가지로 볼 수 있다.

공통 기능은 로깅, 트랜잭션 관리, 보안 등이 있는데, 이러한 공통 기능들을 모든 로직에 각각 삽입하면 코드의 중복이 많아지고 유지보수가 어려워질 수 있다. 또한, 핵심 비즈니스 로직이 공통 기능에 의해 혼란스러워질 수 있어 가독성과 이해도가 떨어지게 된다. 이러한 문제점을 해결하는 방식이 AOP인 것이다.


1. AOP의 주요 용어 정리

아래는 AOP에서 사용되는 주요 용어들이다.

1) Aspect (관점)

Aspect란 공통 관심사를 모듈화한 것이다. 애플리케이션의 비즈니스 로직 외에 공통적으로 필요한 기능(로깅, 트랜잭션 관리, 보안 등)을 Aspect로 정의하게 된다.

2) Join Point (조인 포인트)

Join Point는 Aspect가 적용될 수 있는 실행 시점이다. 스프링 AOP에서는 메서드 실행이 조인 포인트가 되는데, 조인 포인트는 메서드 호출, 예외 발생, 필드 접근 등 다양한 시점을 포함할 수 있다.

3) Advice (어드바이스):

Advice는 특정 조인 포인트에서 실행되는 작업이다. 어드바이스는 Aspect의 실제 구현 부분으로, 언제(전, 후, 예외 발생 시 등) 어떤 작업을 수행할지 정의한다.

4) Pointcut (포인트컷):

Pointcut은 어떤 조인 포인트에서 어드바이스가 실행될지 구체적으로 정의하는 표현식이다. 메서드 이름, 어노테이션, 패키지 등 다양한 기준을 사용하여 조인 포인트를 선택하게 된다. 수많은 비즈니스 메소드 중, 원하는 특정 메소드를 필터링하여 공통 기능을 수행시키기 위해 사용된다.

5) Target Object (타겟 객체):

Target Object는 Aspect의 적용을 받는 객체를 의미한다. 타겟 객체는 조인 포인트에서 실제로 실행되는 비즈니스 로직을 포함하고 있고, 메소드, 클래스 등이 해당된다.


2. 주요 Advice 유형

Aspect의 실제 구현인 Advice의 주요 유형은 다음과 같다.

  • Before
    조인 포인트 실행 전에 실행된다.
  • After
    조인 포인트 실행 후에 실행된다.
  • AfterReturning
    조인 포인트가 정상적으로 종료된 후에 실행된다.
  • AfterThrowing
    조인 포인트가 예외를 던진 후에 실행된다.
  • Around
    조인 포인트 전후에 실행되며, 조인 포인트의 실행을 제어할 수 있다.

3. Advice 실제 적용 예시

아래 예시에서는 CustomerService 클래스의 메서드에 어드바이스를 적용하는 LoggingAspect를 정의하고 있다. 여기서 LoggingAspect는 메서드 호출 시점마다 로그를 남기는 공통 기능을 담당하는 Aspect이다.

@Aspect
@Component
public class LoggingAspect {

    @Before("execution(* com.example.service.CustomerService.*(..))")
    public void logBefore() {
        System.out.println("Before method execution.");
    }

    @After("execution(* com.example.service.CustomerService.*(..))")
    public void logAfter() {
        System.out.println("After method execution.");
    }

    @AfterReturning(pointcut = "execution(* com.example.service.CustomerService.*(..))", returning = "result")
    public void logAfterReturning(Object result) {
        System.out.println("After returning: " + result);
    }

    @AfterThrowing(pointcut = "execution(* com.example.service.CustomerService.*(..))", throwing = "error")
    public void logAfterThrowing(Throwable error) {
        System.out.println("After throwing: " + error.getMessage());
    }

    @Around("execution(* com.example.service.CustomerService.*(..))")
    public Object logAround(ProceedingJoinPoint joinPoint) throws Throwable {
        System.out.println("Around before method execution.");
        Object result;
        try {
            result = joinPoint.proceed();
        } catch (Throwable throwable) {
            System.out.println("Around after throwing.");
            throw throwable;
        }
        System.out.println("Around after method execution.");
        return result;
    }
}
  • logBefore는 메서드 실행 전에 호출된다.
  • logAfter는 메서드 실행 후에 호출된다.
  • logAfterReturning는 메서드가 정상적으로 종료된 후에 호출된다.
  • logAfterThrowing는 메서드가 예외를 던진 후에 호출된다.
  • logAround는 메서드 실행 전후에 호출되며, 메서드 실행을 제어할 수 있다.

위의 예시에서는 CustomerService에 대해서만 로그가 출력되도록 작성되었지만, 만약 "execution(* com.example.service..*(..))" 와 같이 작성한다면 com.example.service 패키지 내의 모든 클래스와 메서드에 대해 로깅을 적용하도록 포인트컷을 정의할 수 있게 되는 것이다.


3. Spring AOP의 특징

Spring Boot AOP(Aspect-Oriented Programming)의 특징을 정리해보면 아래와 같다.

  1. Proxy 기반 AOP 지원
    Spring Boot는 타겟 객체에 대한 프록시를 생성하여 제공한다. 이 프록시는 타겟 객체를 감싸고 실행 시간에 동적으로 생성된다. 프록시는 타겟 객체에 대한 호출을 가로채어 어드바이스(부가기능 로직)를 적용한 후, 타겟의 핵심 기능을 호출한다. 이는 호출 전후에 어드바이스를 적용할 수 있음을 의미한다.

    Proxy란?
    프록시(Proxy)는 대리자라는 뜻으로, 클라이언트가 사용하려고 하는 실제 대상인 것처럼 위장한다. 프록시는 원본 객체에 대한 접근을 대리하고, 호출을 가로채어 추가 기능을 수행하는 중간자 역할을 하는 객체이다.

  2. 메서드 조인 포인트만 지원
    Spring Boot는 동적 프록시를 기반으로 AOP를 구현하기 때문에 메서드 조인 포인트만 지원한다. 이는 런타임 시점에 타겟 메서드가 호출될 때만 부가기능(어드바이스)을 적용할 수 있음을 의미한다.

  3. Spring IoC와의 통합
    Spring AOP는 Spring IoC 컨테이너에서 관리되는 빈에만 AOP를 적용할 수 있다. 이는 AOP 기능이 스프링의 의존성 주입과 밀접하게 통합되어 있음을 의미한다. (즉, AOP를 통해 추가되는 부가기능(어드바이스)도 IoC 컨테이너에 의해 관리된다.) Spring AOP는 중복 코드 제거, 프록시 클래스 작성의 번거로움 해소, 객체들 간의 관계 복잡도 감소 등 엔터프라이즈 애플리케이션에서 자주 발생하는 문제를 해결하는 데 중점을 둔다.

결론적으로, Spring Boot AOP는 프록시 기반의 접근 제어 및 부가기능 추가를 통해 엔터프라이즈 애플리케이션에서의 중복 코드 문제를 해결하고, 스프링 IoC와의 통합을 통해 효율적인 AOP 구현을 지원한다.

profile
전공/개발 지식 정리

0개의 댓글