테스트 코드는 프로젝트의 품질을 보장하는 핵심 도구입니다. 특히 데이터베이스와 연동된 코드를 테스트할 때, 테스트 환경이 실제 데이터베이스와 유사한지 여부는 매우 중요한 요소입니다. 이 글에서는 H2 임베디드 데이터베이스와 Mockito를 사용하는 방식의 차이를 비교하며, 왜 H2 임베디드 데이터베이스가 데이터베이스 연동 테스트에 권장되는지에 대해 다룹니다.
H2 임베디드는 메모리 기반의 경량 데이터베이스로, 실제 데이터베이스와 유사한 환경을 제공합니다. 이를 통해 JPA나 JDBC와 같은 데이터 액세스 로직을 실제 데이터베이스에서 테스트하듯이 검증할 수 있습니다.
H2 임베디드는 실제 SQL 문법과 동작을 지원하므로, 실제 데이터베이스 환경과 유사한 조건에서 테스트를 실행할 수 있습니다.
@SpringBootTest
@AutoConfigureTestDatabase(replace = AutoConfigureTestDatabase.Replace.ANY)
public class UserRepositoryTest {
@Autowired
private UserRepository userRepository;
@Test
public void userSaveTest() {
// Given
User user = new User("test@example.com", "password");
// When
userRepository.save(user);
// Then
User result = userRepository.findByEmail("test@example.com").orElseThrow();
assertEquals("test@example.com", result.getEmail());
}
}
위 예제는 실제 데이터베이스를 사용하는 것처럼 JPA 레포지토리 동작을 테스트합니다.
장점:
H2 임베디드는 단순히 데이터를 저장하는 것을 넘어, 애플리케이션과 데이터베이스 간의 연동을 포함한 통합 테스트를 가능하게 합니다.
이는 단순 로직 테스트를 넘어 애플리케이션 전체의 동작을 검증할 수 있는 강력한 도구가 됩니다.
Mockito는 주로 단위 테스트에서 레포지토리, 서비스, 컨트롤러의 특정 메서드를 모킹(mocking)하여 테스트하는 데 사용됩니다.
@ExtendWith(MockitoExtension.class)
public class UserServiceTest {
@Mock
private UserRepository userRepository;
@InjectMocks
private UserService userService;
@Test
public void findUserTest() {
// Given
User mockUser = new User("test@example.com", "password");
Mockito.when(userRepository.findByEmail("test@example.com")).thenReturn(Optional.of(mockUser));
// When
User result = userService.findUserByEmail("test@example.com");
// Then
assertEquals("test@example.com", result.getEmail());
}
}
Mockito를 사용하면 특정 레포지토리 메서드의 동작을 모킹하여, 반환값을 미리 설정하고 로직을 검증할 수 있습니다.
Mockito는 테스트 환경에서 실제 데이터베이스와 독립적으로 동작하므로 아래와 같은 한계가 존재합니다:
레포지토리 구현 검증 실패
@Query
로 작성한 JPQL이 실제 데이터베이스에서 실행되지 않을 경우, Mockito 테스트에서는 이를 검출하지 못합니다.엔티티 매핑 검증 부족
@Column
, @OneToMany
등 데이터베이스와의 매핑이 잘못되었을 때 오류를 발견할 수 없습니다.테스트 신뢰도 저하
결론적으로, H2 임베디드는 데이터베이스와 연동된 애플리케이션의 테스트에서 테스트 신뢰도를 높이는 가장 적합한 도구입니다.
Mockito는 단위 테스트에서는 유용하지만, 실제 데이터베이스와 관련된 문제를 발견하는 데는 한계가 있습니다.
요약:
테스트의 목표는 단순히 테스트 코드를 작성하는 것이 아니라, 실제로 발생할 수 있는 오류를 조기에 발견하여 프로젝트의 품질을 높이는 데 있습니다.