이전 강의에서는 DB접근 기술에 대해서 알아보았다.
이번시간에는 AOP에 대해서 실습해보자.
국비학원 다니면서 잠깐 짚고 넘어갔던 부분인데 기억이 안나구나...다시 복습해보자
1. AOP 가 필요한 상황
내가 회사에 가서 일을 하고 있는데 과장님이 " 도비사원 기능이 실행하는데 걸리는 시간을 측정해줘 " 라고 했을때
지금은 회원가입 및 회원조회 같은 서비스만 있는데 실무에서는 서비스가 엄청 많을 것이다.
그걸 하나하나 다 걸리는 시간을 측정하고 있다면, 하루종일 하고 있을 것이다.
@Transactional
public class MemberService {
private final MemberRepository memberRepository;
public MemberService(MemberRepository memberRepository){
this.memberRepository = memberRepository;
}
/**
* 회원가입
*/
public Long join(Member member){
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");
}
}
/**
* 전체 회원 조회
*/
public List<Member> findMembers(){
long start = System.currentTimeMillis();
try {
return memberRepository.findAll();
} finally {
long finish = System.currentTimeMillis();
long timeMs = finish - start;
System.out.println(timeMs);
}
}
}
이렇게 작성해서 메소드 호출 시간을 확인 할 수 있고, 만약 그림을 그린다면 아래와 같다.
하지만 아까도 말했듯이 이렇게 하게 된다면 유지보수가 어려울 뿐더라 모든 로직을 찾아서
위와 같이 하나하나 코드를 추가하고 변경해야한다.
이럴때 우리는 공통 관심사항(cross-cutting concern)과 핵심 관심사항(core concern)으로 나눠서 분류를 해야한다.
- 공통 관심사항(cross-cutting concern) : 실행하는데 걸리는 시간
- 핵심 관심사항(core concern) : 회원가입, 회워조회 같은 비즈니스 로직
회원 가입, 회원 조회와 같은 비즈니스 로직과 같은 경우가 핵심 관심사항이고,
이러한 기능 실행하는데 걸리는 시간을 측정하는 것과 같은 기능은 공통 관심 사항으로 분류된다.
우리는 이럴 때 AOP의 필요성을 느낀다! 왜 얼마나 편하길래 ?
2. AOP 적용
이전에는 로직들을 시간측정 로직을 메서드에 하나하나 다 붙였지만
AOP 는 시간측정로직을 구현하고 내가 원하는 곳에 적용하는 것이 바로 AOP이다.
오? 이게 된다고 ? 그렇다면 실습을 통해 알아보자 !
(1) TimeTraceAop 클래스 생성
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
@Component
public class TimeTraceAop {
@Around("execution(*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");
}
}
}
메서드가 AOP 기능을 할 수 있도록 @Aspect 어노테이션을 사용하고
스프링 빈으로 등록하기 위해 @Component로 스프링 빈으로 등록 한다 !
이제 웹 애플리케이션을 실행해서 시간 측정이 정상적으로 동작하는지 로그를 확인해 보자.
회원가입 후 회원목록으로 가입된 회원 확인까지 한 로그이다.
우리가 작성한 코드대로 START와 END가 출력된 것을 볼 수 있다.
3. AOP 동작방식
(1) AOP 적용 전 의존관계
: 회원 컨트롤러와 회원 서비스는 각 스프링 빈으로 컨테이너에 등록되어 있고,
회원 컨트롤러는 회원 서비스를 의존하고 있다.
(2) AOP 적용 후 의존관계
: 회원 컨트롤러에서 회원 서비스가 호출될 때 실제 회원 서비스가 아닌 프록시 회원 서비스가
호출되고, joinPoint.proceed()가 호출되면 실제 회원 서비스의 메서드들이 동작한다.
(3) AOP를 적용하기 전 후의 전체 모습
@Around를 통해 프로젝트 전체 메서드에 AOP가 적용되었기 때문에
컨테이너에 스프링 빈으로 등록되는 것들이 모두 프록시와 같이 등록된 것을 확인할 수 있다.
'ON > 실습' 카테고리의 다른 글
[Spring Boot] 스프링 DB 접근 기술 - 스프링 데이터 JPA (1) | 2023.11.29 |
---|---|
[Spring Boot] 스프링 DB 접근 기술 - JPA (0) | 2023.11.28 |
[Spring Boot] 스프링 DB 접근 기술 - 순수 JDBC 와 JdbcTemplate (0) | 2023.11.27 |
[Spring Boot] 회원 관리 예제 - 웹 MVC 개발 ① (0) | 2023.11.24 |
[Spring Boot] 스프링 빈과 의존관계 - 자바 코드로 직접 스프링 빈 등록하기 ② (0) | 2023.11.23 |