Test

[Test] Mockito와 단위 테스트 개념

감자b 2024. 12. 30. 00:19

단위 테스트란?

단위 테스트는 각 기능이나 모듈이 의도한 대로 작동하는지를 검증하는 테스트 방법으로 개발자가 작성한 코드의 작은 단위, 즉 함수나 메서드 단위로 진행된다.

이는 각 기능 별로 독립적으로 테스트하여 코드의 품질을 높이고, 버그를 조기에 발견할 수 있는 장점이 있다.

통합 테스트

  • 목적: 여러 모듈 또는 클래스가 서로 상호작용할 때 시스템이 올바르게 동작하는지 확인하는 테스트 방법으로전체적인 동작을 테스트하기 때문에 시스템의 안정성을 검증하는 데 중요하다.
  • 실제 데이터베이스, 파일 시스템 등 외부 의존성을 포함하여 실행 시간이 길다.

자바 언어의 경우 JUnit 프레임워크를 활용해서 단위 테스트를 수행할 수 있다.

테스트 코드는 주로 Given/When/Then 패턴을 사용하여 작성한다.

  • Given : 테스트를 위한 어떠한 데이터가 주어질 때
    • 테스트에 필요한 변수 정의, Mock 객체 정의 등
  • When : 테스트를 실행할 때
    • 테스트하려는 메서드를 실행
  • Then : 테스트의 기댓값 검증
    • When 절에서 메서드를 실행하였을 때 기대하는 값
 @Test
 @DisplayName("Test")
 void test() {
     // Given

     // When

     // Then
}

Mockito

Mockito란 자바에서 객체를 모킹(mocking)하기 위한 프레임워크로, 실제 객체 대신 모의 객체를 사용하여 의존성을 주입하고 테스트할 수 있도록 한다.

@Mock, @InjectMocks 등 어노테이션을 통해 모의 객체를 쉽게 생성하고 사용할 수 있다.

즉 Mockito는 단위 테스트에서 의존성이 있는 객체를 모킹하여 테스트할 수 있게 한다.

스프링의 경우 일반적으로 Controller → Service → Repository 구조로 의존성을 가진다.

@Service
public class UserService {
    private final UserRepository userRepository;

    public UserService(UserRepository userRepository) {
        this.userRepository = userRepository;
    }

    public User findUserById(Long id) {
        return userRepository.findById(id).orElse(null);
    }
}

이렇게 데이터베이스 또는 외부 서비스에 의존하는 클래스의 메서드를 테스트할 때, 실제 데이터를 사용하는 대신 Mockito를 통해 모의 객체를 사용함으로써 외부 의존성을 제거할 수 있다.

이는 테스트를 독립적으로 실행할 수 있어, 테스트의 신뢰성과 속도를 높일 수 있다.

@ExtendWith(MockitoExtension.class)
class UserServiceTest {

    @Mock
    private UserRepository userRepository; // UserRepository의 모의 객체

    @InjectMocks
    private UserService userService; // UserService 인스턴스 (모의 객체 주입)

    @Test
    void testFindUserById_UserDoesNotExist() {
        // Given
        when(userRepository.findById(1L)).thenReturn(Optional.empty()); // findById 호출 시 빈 Optional 반환

        // When
        User result = userService.findUserById(1L); // 서비스 메서드 호출

        // Then
        assertNull(result); // 결과가 null임을 확인
    }
}
  • @ExtendWith(MockitoExtension.class): JUnit 5에서 Mockito 기능을 사용할 수 있도록 설정
  • @Mock: UserRepository의 모의 객체를 생성
  • @InjectMocks: UserService의 인스턴스를 생성하고, 모의 객체를 주입

이렇게 하면 실제 데이터베이스에 연결하지 않고도 필요한 메서드만 단위 테스트를 할 수 있다.