使用Mockito Mock含Lambda参数方法时无法找到正确的ArgumentMatcher
问题根因
你遇到的匹配失败不是Lambda的问题,本质是JdbcTemplate的query方法存在多个参数列表高度相似的重载,你之前的写法存在泛型推断歧义,导致Mockito定位不到你要Mock的目标重载方法。Lambda作为函数式接口的实现实例,本身是可以被对应接口类型的匹配器正常匹配的。
可行解决方案
方案1:显式指定匹配器泛型类型(最推荐)
通过显式声明any()的泛型类型,消除重载匹配歧义,代码如下:
import static org.mockito.ArgumentMatchers.*; @Test void testSomething(){ List<Model> models = new ArrayList<>(); // 构造测试数据逻辑省略 doReturn(models) .when(jdbcTemplate) .query( anyString(), any(Object[].class), ArgumentMatchers.<RowMapper<Model>>any() ); // 后续测试逻辑省略 }
如果用的是Mockito 3.1+版本,也可以用更简洁的isA()写法:
doReturn(models) .when(jdbcTemplate) .query( anyString(), any(Object[].class), isA(RowMapper.class) );
方案2:自定义参数匹配器
如果需要更灵活的匹配规则,可以用argThat自定义匹配逻辑:
doReturn(models) .when(jdbcTemplate) .query( anyString(), any(Object[].class), argThat(mapper -> mapper instanceof RowMapper) );
注意踩坑点
务必确认你Mock的参数顺序和业务代码实际调用的参数顺序完全一致,JdbcTemplate存在两个参数顺序不同的query重载,很容易搞混:
- 你业务代码调用的重载:
query(String sql, Object[] 参数数组, RowMapper 行映射器) - 另一个易混淆的重载:
query(String sql, RowMapper 行映射器, Object... 可变参数)
如果参数顺序写反,无论用什么匹配器都无法命中Mock规则。
内容的提问来源于stack exchange,提问作者ThrowableException
相关产品推荐
相关产品推荐

