You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

编写saveColor单元测试时遇modelMapper.map()未调用错误求助

问题原因与解决方案

核心问题分析

1. Mock对象未被Spring容器使用

你在测试类中用@Mock标注ModelMapper,但@Mock仅会创建一个mock对象,不会替换Spring上下文里的真实ModelMapper实例。Controller依赖的是Spring容器中的真实ModelMapper,而非你mock的对象,所以自然不会触发mock对象的map方法,导致verify校验失败。

2. 请求参数可能未通过校验

测试用例中colorDTO的hex值为"1##r",如果ColorDTO的hex字段带有校验注解(比如@Pattern要求合法十六进制格式),这个值会触发校验错误,bindingResult会存在错误信息,代码直接返回HttpStatus.BAD_REQUEST,根本不会执行到modelMapper.map()的逻辑。


具体修复步骤

步骤1:替换@Mock为@MockBean

将测试类中的@Mock private ModelMapper modelMapper;改为@MockBean private ModelMapper modelMapper;。@MockBean会自动将mock对象注入Spring容器,替换掉原本的真实ModelMapper实例,确保Controller使用的是你mock的对象。

步骤2:使用合法的请求参数

修改colorDTO的hex值为符合校验规则的内容,比如合法的十六进制颜色值"#FF0000",确保校验通过,代码能执行到modelMapper.map()的逻辑。

步骤3:优化Mock匹配逻辑(可选)

建议使用any(ColorDTO.class)和eq(Color.class)来匹配方法参数,避免因对象equals判断失败导致mock不生效。


修改后的测试代码示例

@SpringBootTest
@AutoConfigureMockMvc
public class ColorMasterControllerTest {

    @Autowired
    private MockMvc mockMvc;
    @Autowired
    private ObjectMapper objectMapper;
    @MockBean // 替换为@MockBean
    private ModelMapper modelMapper;
    @MockBean
    private ColorMaster colorMaster;

    @Test
    void savedColor_ValidInput_ReturnCreated() throws Exception {
       
        // 使用合法的十六进制颜色值
        ColorDTO colorDTO = new ColorDTO(1L, "red", "#FF0000");
        Color color = new Color(1L, "red", "#FF0000");

        // 优化参数匹配逻辑
        when(modelMapper.map(any(ColorDTO.class), eq(Color.class))).thenReturn(color);
        when(colorMaster.saveColor(any(Color.class))).thenReturn(color);

        MvcResult result = mockMvc.perform(post("/api/color")
                .contentType(MediaType.APPLICATION_JSON)
                .content(objectMapper.writeValueAsString(colorDTO)))
                .andExpect(status().isCreated())
                .andReturn();
       
        verify(modelMapper, times(1)).map(any(ColorDTO.class), eq(Color.class));
        verify(colorMaster, times(1)).saveColor(any(Color.class));
        then(result.getResponse().getContentAsString()).isEqualTo(objectMapper.writeValueAsString(color));
    }
}

额外优化建议

如果仅需测试Controller逻辑,推荐使用@WebMvcTest(ColorMasterController.class)代替@SpringBootTest,它只会加载Controller相关组件,测试启动更快、更轻量化:

@WebMvcTest(ColorMasterController.class)
@ExtendWith(MockitoExtension.class)
public class ColorMasterControllerTest {
    // 后续代码与上述修改一致
}

内容的提问来源于stack exchange,提问作者Art yudi

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.01 13:58:13