Spring Boot中如何Mock数据库并解决测试连接拒绝问题?
解决方案
核心思路
测试时要避免加载数据库相关的自动配置,同时用Mock替代真实的JpaRepository实例,阻止Spring尝试连接PostgreSQL。
方案一:仅测试Web层(推荐)
用@WebMvcTest注解,它只会加载Controller层相关的Bean,自动排除数据库、JPA等无关配置,是Web接口测试的最优选择:
@WebMvcTest(ReaderController.class) class ReaderControllerTest { @Autowired private MockMvc mockMvc; // 用@MockBean替换真实的ReaderRepository @MockBean private ReaderRepository readerRepository; @Autowired private ObjectMapper objectMapper; @Test void testPostReader() throws Exception { // 构造测试用例 Reader request = new Reader(null, "张三"); Reader mockSavedReader = new Reader(1L, "张三"); // Mock save方法的返回值 when(readerRepository.save(any(Reader.class))).thenReturn(mockSavedReader); // 发起POST请求并验证结果 mockMvc.perform(post("/reader") .contentType(MediaType.APPLICATION_JSON) .content(objectMapper.writeValueAsString(request))) .andExpect(status().isOk()) .andExpect(jsonPath("$.id").value(1L)) .andExpect(jsonPath("$.name").value("张三")); } }
方案二:全上下文测试(需排除数据库配置)
如果必须加载完整Spring上下文(比如需要其他非Web层Bean),则通过@EnableAutoConfiguration排除数据库相关的自动配置类:
@SpringBootTest @AutoConfigureMockMvc // 排除数据源、JPA相关的自动配置 @EnableAutoConfiguration(exclude = { DataSourceAutoConfiguration.class, DataSourceTransactionManagerAutoConfiguration.class, HibernateJpaAutoConfiguration.class }) class ReaderApplicationTest { @Autowired private MockMvc mockMvc; @MockBean private ReaderRepository readerRepository; @Autowired private ObjectMapper objectMapper; // 测试方法同方案一 }
常见问题排查
- 之前注解无效的原因:
- 误用
@SpringBootTest却未排除数据库自动配置,Spring仍会尝试初始化PostgreSQL连接 - 未用
@MockBean替换真实的Repository,导致代码调用了真实的JPA save方法,触发数据库连接
- 误用
- 避免使用
@DataJpaTest:该注解专门用于测试JPA层,会自动启动嵌入式数据库,不符合你禁用数据库的需求
内容的提问来源于stack exchange,提问作者s1n7ax
相关产品推荐
相关产品推荐

