상세 컨텐츠

본문 제목

[스프링 핵심 원리 - 입문] week06

[SW]/[Spring 스터디] 2022

by 시원00 2022. 9. 11. 14:20

본문

스프링 입문 - 코드로 배우는 스프링 부트, 웹 MVC, DB 접근 기술

https://www.inflearn.com/course/스프링-입문-스프링부트/dashboard

 

섹션 7. AOP

 

7.1 AOP가 필요한 상황

  • 모든 메소드의 호출 시간을 측정하고 싶다면?
  • 공통 관심 사항(cross-cutting concern) vs 핵심 관심 사항(core concern)
  • 회원 가입 시간, 회원 조회 시간을 측정하고 싶다면?

 

MemberService 회원 조회 시간 측정 추가

  • 가장 기본적인 방법
    • 시작 시간과 종료 시간 측정 후, '종료 시간 - 시작 시간' 넘기기

 

join()

MemberService.java - join() 부분

public Long join(Member member) {
		// 회원 조회 시간 측정
        // 시작할 때 시간 측정 + 끝날 때 시간 측정 try-finally 문 이용
        long start = System.currentTimeMillis();
        try {
            validateDuplicateMember(member);    // 중복 회원 검증

            memberRepository.save(member);
            return member.getId();
        } finally {
            long finish = System.currentTimeMillis();
            long timeMs = finish - start;
            System.out.println("join = " + timeMs + "ms");
        }
}

test 실행 : join 시간 확인 가능

 

findMembers()

findMembers() 부분

    // 전체 회원 조회
    public List<Member> findMembers() {
        // 시간 측정
        long start = System.currentTimeMillis();
        try {
            return memberRepository.findAll();
        } finally {
            long finish = System.currentTimeMillis();
            long timeMs = finish - start;
            System.out.println("findMembers = " + timeMs + "ms");
        }
    }

 

문제

  • 회원가입, 회원 조회에 시간을 측정하는 기능은 핵심 관심 사항이 아니다.
  • 시간을 측정하는 로직은 공통 관심 사항이다.
  • 시간을 측정하는 로직과 핵심 비즈니스의 로직이 섞여서 유지보수가 어렵다.
  • 시간을 측정하는 로직을 별도의 공통 로직으로 만들기 매우 어렵다.
  • 시간을 측정하는 로직을 변경할 때 모든 로직을 찾아가면서 변경해야 한다.

 

 

7.2 AOP 적용

  • AOP: Aspect Oriented Programming
  • 공통 관심 사항(cross-cutting concern) vs 핵심 관심 사항(core concern) 분리

 

시간 측정 AOP 등록

  • main/java/hello.hellospring : aop (package) 생성
  • main/java/hello.hellospring/aop : TimeTraceAop.java 생성

TimeTraceAop.java

package hello.hellospring.aop;

import org.aspectj.lang.ProceedingJoinPoint;
import org.aspectj.lang.annotation.Around;
import org.aspectj.lang.annotation.Aspect;
import org.springframework.stereotype.Component;

@Aspect //aop로 사용하기 위해 필수
@Component    // @Component로 사용해도 되지만, spring bean에 등록해서 사용해도 됨
public class TimeTraceAop {

    @Around("execution(* hello.hellospring..*(..))")    //hello.hellospring 패키지 하위 파일 모두 적용
    public Object execute(ProceedingJoinPoint joinPoint) throws Throwable {
        // 시간 로직
        long start = System.currentTimeMillis();
        System.out.println("START: " + joinPoint.toString());
        try {
            return joinPoint.proceed();
        } finally {
            long finish = System.currentTimeMillis();
            long timeMs = finish - start;
            System.out.println("END: " + joinPoint.toString() + " " + timeMs + "ms");
        }
    }
}

 

해결

  • 회원 가입, 회원 조회 등 핵심 관심 사항과 시간을 측정하는 공통 관심 사항을 분리한다.
  • 시간을 측정하는 로직을 별도의 공통 로직으로 만들었다.
  • 핵심 관심 사항을 깔끔하게 유지할 수 있다.
  • 변경이 필요하면 이 로직만 변경하면 된다.
  • 원하는 적용 대상을 선택할 수 있다.
    • 서비스만 측정: * hello.hellospring.service..*(..) 서비스 하위 파일만 측정

 

스프링의 AOP 동작 방식 설명

 

AOP 작용 전 의존 관계

 

  • memberController가 memberService 의존
  • memberController가 memberService에서 메서드 호출

 

AOP 적용 후 의존관계

  • 프록시: aop가 있으면 가짜 memberService를 만들어냄
  • memberController가 호출하는 memberService는 프록시

 

실제 Proxy 주입 확인 - 콘솔에 출력

MemberController.java

System.out.println("memberService = " + memberService.getClass());
  • 출력 결과에 class hello.hellospring.service.MemberService 뒤에 $$EnhancerBySpringCGLIB$$95f6ac95가 추가로 붙는 것 확인
    • 멤버 서비스를 복제해서 코드 조작

 

AOP 적용 전 전체 그림

 

AOP 적용 후 전체 그림

 

 

섹션 8. 다음으로

  • 지금까지 스프링으로 웹 애플리케이션을 개발하는 방법에 대해서 얇고 넓게 학습했다. 이제부터는 각각의 기술들을 깊이있게 이해해야 한다.
  • 거대한 스프링의 모든 것을 세세하게 알 필요는 없다. 우리는 스프링을 만드는 개발자가 아니다. 스프링을 활용해서 실무에서 발생하는 문제들을 잘 해결하는 것이 훨씬 중요하다. 따라서 핵심 원리를 이해하고, 문제가 발생했을 때, 대략 어디쯤부터 찾아들어가면 될지, 필요한 부분을 찾아서 사용할 수 있는 능력이 더 중요하다.

 

스프링 완전 정복 시리즈 - 강의 목록

  • 스프링 핵심 원리
  • 스프링 웹 MVC
  • 스프링 DB 접근 기술
  • 스프링 부트

 

스프링 부트와 JPA 실무 완전 정복 로드맵 - 강의 목록

  • 자바 ORM 표준 JPA 프로그래밍
  • 실전! 스프링 부트와 JPA 활용1 - 웹 애플리케이션 개발
  • 실전! 스프링 부트와 JPA 활용2 - API 개발과 성능 최적화
  • 실전! 스프링 데이터 JPA
  • 실전! Querydsl

 

 

FIN.

 

 


관련글 더보기

댓글 영역