【问题标题】:Is it required for spring boot application to be connected to database when performing unit test执行单元测试时spring boot应用程序是否需要连接到数据库
【发布时间】:2021-01-16 01:49:42
【问题描述】:

我正在为服务层编写单元测试用例。这是我的服务类:

@Service
@RequiredArgsConstructor
public class EmpService {

    private final EmpRepository empRepository;

    public EmployeeDto findById(UUID id) {
        return empRepository.findById(id).map(this::mapToEmployeeDto);
    }
}

测试类:

@SpringBootTest
class EmpServiceTest {
    @Autowired
    EmpService empService;
    
    @MockBean
    EmpRepository empRepository;
    
    @Test
    void get_employee_by_id_success_case() throws IOException {

        UUID empId = UUID.fromString("2ec828f5-35d5-4984-b783-fe0b3bb8fbef"); 
        EmployeeDto expectedEmp = new EmployeeDto(empId, "James");
        EmployeeEntity stubbedEmployee = new EmployeeEntity(empId, "James");
        when(empRepository.findById(any(UUID.class)))
            .thenReturn(Optional.of(stubbedEmployee));
        EmployeeDto actualEmp = empService.findById(empId);
        assertEquals(expectedEmp, actualEmp);
    }
}

我正在为我的数据库 (postgres) 使用 docker 图像。当容器为db启动时,上面的测试用例就运行成功了。

但是当我停止整个 docker 应用程序时,会出现以下错误:

java.lang.IllegalStateException: Failed to load ApplicationContext
Caused by: org.springframework.beans.factory.BeanCreationException: Error creating bean with name 'empRepository' defined in repo.EmpRepository defined in @EnableJpaRepositories declared on JpaRepositoriesRegistrar.EnableJpaRepositoriesConfiguration: Cannot resolve reference to bean 'jpaMappingContext' while setting bean property 'mappingContext'; nested exception is org.springframework.beans.factory.BeanCreationException: Error creating bean with name 'jpaMappingContext': Invocation of init method failed; nested exception is javax.persistence.PersistenceException: [PersistenceUnit: default] Unable to build Hibernate SessionFactory; nested exception is org.hibernate.exception.JDBCConnectionException: Unable to open JDBC Connection for DDL execution

单元测试用例不应该独立于数据库,特别是当我们模拟 repo bean 时?

想象一个人在他们的机器上重新签出这段代码,并在没有设置数据库的情况下首先构建项目。在这种情况下,单元测试应该运行并且不应该依赖于数据库。

请注意我使用的是 JUnit 5 (Jupiter),spring-boot-starter-test kit。

【问题讨论】:

  • @Kayaman 用于代码覆盖。目前应用还处于非常初级的阶段。随着时间的推移,更多的逻辑将被添加到其中。您可以认为测试是检查是否在愉快的情况下返回了正确的 dto。
  • 您已自动连接 EmpService,它必须连接到存储库。尝试模拟 EmpService。
  • @MS- 如果我这样做,那么我将如何调用我想要测试的方法
  • @SpringBootTest 加载应用程序上下文,这就是 bean 创建失败的原因。

标签: java spring-boot jpa junit mockito


【解决方案1】:

在我看来,你写的更多的是集成测试,而不是单元一。

除了语义,还有一个非常好的框架testcontainers,它将在docker容器中运行数据库,只是为了测试阶段。

这篇文章展示了如何设置此类数据库测试:https://programmerfriend.com/spring-boot-integration-testing-done-right/

【讨论】:

    猜你喜欢
    • 2017-01-30
    • 2021-06-17
    • 2015-05-31
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2020-02-18
    • 2020-05-17
    • 2017-11-24
    相关资源
    最近更新 更多