首页
学习
活动
专区
圈层
工具
发布
首页
学习
活动
专区
圈层
工具
MCP广场
社区首页 >问答首页 >使用Mockito注入DozerBeanMapper

使用Mockito注入DozerBeanMapper
EN

Stack Overflow用户
提问于 2018-04-20 18:27:05
回答 3查看 3.8K关注 0票数 2

我在Spring服务中使用了Dozer。如何使用JUnit和Mockito将DozerBeanMapper注入到测试的服务中?

我的java类(如果经过简化)如下所示:

代码语言:javascript
运行
复制
@Service
public class UnicornService {
    private final DozerBeanMapper dozer;

    @Autowired
    public UnicornService(DozerBeanMapper dozer) {
        this.dozer = dozer;
    }

    public UnicornDto convert(Unicorn unicorn) {
        return dozer.map(unicorn, UnicornDto.class);
    }
}

使用JUnit 4+ Mockito + Hamcrest的测试类如下所示:

代码语言:javascript
运行
复制
import static com.shazam.shazamcrest.MatcherAssert.assertThat;
import static com.shazam.shazamcrest.matcher.Matchers.sameBeanAs;

@RunWith(MockitoJUnitRunner.class)
public class UnicornServiceTest {
    @Mock
    private DozerBeanMapper dozer;
    @InjectMocks
    private UnicornService unicornService;

    @Test
    public void testConvert() throws Exception {
        final Unicorn original = ...
        final UnicornDto expected = ...

        // Execute the method being tested
        final UnicornDto result = unicornService.convert(original);
        // Validation
        assertThat(result, sameBeanAs(expected));
    }
}

问题是模拟的Dozer实例没有像预期的那样映射对象-默认情况下,Mockito存根返回空或null对象。如果我从测试中删除@Mock注释,它将抛出NPE!

EN

回答 3

Stack Overflow用户

发布于 2018-04-20 18:27:05

DozerBeanMapper对象上使用@Spy注释。这将允许您调用对象的所有常规方法,同时此对象仍由Mockito管理(作为模拟)并注入到测试的服务中。

代码语言:javascript
运行
复制
@RunWith(MockitoJUnitRunner.class)
public class UnicornServiceTest {
    @Spy
    private DozerBeanMapper dozer;
    @InjectMocks
    private UnicornService unicornService;
    // ...   
票数 4
EN

Stack Overflow用户

发布于 2018-04-20 18:32:46

我找到的另一个解决方案是重构你的代码。它对我来说似乎不那么有吸引力,因为仅仅为了编写测试,它弊大于利。

在服务中通过setter使用注入

代码语言:javascript
运行
复制
@Service
public class UnicornService {
    private DozerBeanMapper dozer;

    @Autowired
    public setDozer(DozerBeanMapper dozer) {
        this.dozer = dozer;
    }

    public UnicornDto convert(Unicorn unicorn) {
        return dozer.map(unicorn, UnicornDto.class);
    }
}

重构测试:

代码语言:javascript
运行
复制
@RunWith(MockitoJUnitRunner.class)
public class UnicornServiceTest {
    @InjectMocks
    private UnicornService unicornService;

    @Before
    public void injectDozer() {
        final DozerBeanMapper dozer = new DozerBeanMapper();
        unicornService.setDozer(dozer);
    }
    // ...
票数 0
EN

Stack Overflow用户

发布于 2018-04-20 18:34:12

您根本不应该依赖映射器创建适当的对象,而只是服务调用映射器并返回其结果。应该在映射器的单元测试中测试实际的映射。即

代码语言:javascript
运行
复制
@RunWith(MockitoJUnitRunner.class)
public class UnicornServiceTest {
    @Mock
    private DozerBeanMapper dozer;
    @InjectMocks
    private UnicornService unicornService;

    @Test
    public void testConvert() throws Exception {
        final Unicorn original = mock(Unicorn.class);
        final UnicornDto expected = mock(UnicornDto.class);
        when(dozer.map(original, UnicornDto.class)).thenReturn(expected);

        // Execute the method being tested
        final UnicornDto result = unicornService.convert(original);
        // Validate that the call was delegated to the mapper
        assertThat(result, is(expected));
    }
}
票数 0
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/49939544

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档