[스프링 입문] 회원 서비스 테스트

enxnong·2023년 4월 23일
0

Spring

목록 보기
13/26

김영한님의 스프링 입문 - 코드로 배우는 스프링 부트, 웹 MVC, DB 접근 기술을 보면서 공부한 내용입니다.

만들어둔 Service를 테스트해보자
Test 클래스는 Ctrl + shift + T 를 누르면 자동으로 생성할 수 있다.
테스트케이스를 작성할 때

  1. given (이런 상황이 주어져서)

  2. when (이걸 실행했을 때)

  3. then (결과는 이것이 나와야돼)

의 세 단계를 거쳐 코드를 작성하면 편리하다.

회원 가입

@Test
    void 회원가입() {
        // Test는 한글로 바꿔도 상관없다

        // given (이런 상황이 주어져서)
        Member member = new Member();
        member.setName("hello");

        // when (이걸 실행했을 때)
        Long saveId = memberService.join(member);

        // then (결과는 이것이 나와야돼)
        Member findMember = memberService.findOne(saveId).get();
        assertThat(member.getName()).isEqualTo(findMember.getName()); // 이름 검증
    }

이렇게 회원가입 테스트케이스를 작성하면 잘 통과가 된다.

하지만 Test는 예외처리가 가장 중요하다!

이름이 중복되는 사람의 회원가입은 안된다라는 조건이 있었다. 이러한 조건이 제대로 실행되는지 확인하기 위해 새로운 Test케이스를 작성한다.

회원 가입 중복X

@Test // 테스트는 예외처리가 제일 중요하다
    public void 중복_회원_예외(){

        // given
        Member member1 = new Member();
        member1.setName("spring");

        Member member2 = new Member();
        member2.setName("spring");

        // when
        memberService.join(member1);
        // memberService.join(member2); // 이름이 동일하므로 예외가 발생해야됨

        // then
        /*
         예외처리 방법1
        try {
            memberService.join(member2);
            fail();
        } catch (IllegalStateException e) {
            assertThat(e.getMessage()).isEqualTo("이미 존재하는 회원입니다.");
        }
        */

        // 예외처리 방법2
        IllegalStateException e = assertThrows(IllegalStateException.class, () -> memberService.join(member2));
        // member2를 넣으면 IllegalStateException 예외가 발생해야됨

        assertThat(e.getMessage()).isEqualTo("이미 존재하는 회원입니다.");
    }
💡 assertThrows란?
메소드는 첫번째 인자로 발생할 예외 클래스의 Class 타입을 받고, 두번째 인자로 람다식을 받는다. 람다식에서 예외가 발생할 경우 Class 타입과 발생한 예외가 같은 타입인지 체크한다.

메모리 삭제

테스트 케이스가 끝날 때마다 메모리를 clear해서 순서 상관없이 코드가 실행되는지 확인해야된다.

MemoryMemberRepository memberRepository = new MemoryMemberRepository();

@AfterEach
public void afterEach(){
    memberRepository.clearStore();
}

하지만!!

new ~ 로 다른 객체 레파지토리가 생성되면 다른 인스턴스이기 때문에 내용물이 달라질 수 있다. 이를 해결하기 위해 같은 레파지토리를 이용하도록 설정해야된다.

동일한 인스턴스 공유하는 방법

  1. MemberService 클래스를 다음과 같은 코드로 변경한다
private final MemberRepository memberRepository;

    // Constructor 단축키 : alt + insert
    public MemberService(MemberRepository memberRepository) {
        this.memberRepository = memberRepository; // 생성자를 이용해 외부에서 주입하기
    }
  1. MemberServiceTest 클래스에서 MemberRepository를 주입
MemberService memberService;
MemoryMemberRepository memberRepository;

@BeforeEach
public void beforeEach(){
    memberRepository = new MemoryMemberRepository();
    memberService = new MemberService(memberRepository);
    // 테스트가 실행될 때마다 MemberService와 같은 메모리 리퍼지토리가 사용된다.
}

이렇게 하면

테스트가 실행될 때마다 각각 MemoryMemberRepository 가 생성되고 memberService 에 주입함으로써 같은 인스턴스를 사용하게 된다.

💡 즉, `MemoryService`입장에서 보면 외부에서 `MemoryMemberRepository`를 주입해줌 → **Dependency Injection (DI:의존성 주입)**
profile
높은 곳을 향해서

0개의 댓글