问题描述
我进行了以下测试:
@SpringBoottest(classes = {SomeService.class,DtoMapperImpl.class})
class SomeServiceTest {
以及以下映射器:
@Mapper(componentModel = "spring")
public interface DtoMapper {
EntityDto toDto(Entity entity);
}
我没有更改软件包(这意味着 DtoMapperImpl 与 DtoMapper 位于同一软件包中)
将Impl更改为接口后,我的测试就会失败:
@SpringBoottest(classes = {SomeService.class,DtoMapper.class})
class SomeServiceTest {
原因: org.springframework.beans.factory.UnsatisfiedDependencyException: 创建名称为“ someService”的bean时出错:不满意的依赖关系 通过构造函数参数2表示;嵌套异常为 org.springframework.beans.factory.NoSuchBeanDeFinitionException:否 可用类型为“ DtoMapper”的合格Bean:预计至少为1 符合自动装配候选条件的bean。依赖项注释:{}
能否请您提出解决此问题的最佳方法?我正在使用MapStruct 1.3.1.Final
解决方法
创建以下配置(应该指出映射器的位置):
@TestConfiguration
@ComponentScan("some.package.mapper")
public class MappersConfig {
}
并修改切片:
@SpringBootTest(classes = {SomeService.class,MappersConfig.class})
class SomeServiceTest {
,
问题实际上与MapStruct无关,而与SpringBootTest#classes
的使用方式有关。
classes
中的SpringBootTest
旨在提供应在测试中加载的组件。
来自JavaDoc:
用于加载
ApplicationContext
的组件类。也可以使用@ContextConfiguration(classes=...)
指定。如果未定义显式类,则测试将寻找嵌套的@Configuration
类,然后退回到@SpringBootConfiguration
搜索。 返回值: 用于加载应用程序上下文的组件类
在您的情况下,您有2个课程:
-
SomeService
-我假设这是一个用@Service
注释的类,Spring会正确地加载它 -
DtoMapper
-这是MapStruct映射器,它是一个接口,不是组件。您要测试的组件是DtoMapperImpl
您可以通过以下几种方法来解决此问题:
使用Impl类
您可以在DtoMapperImpl
中使用SpringBootTest#classes
(Spring Component类),然后您的测试将加载正确的组件
使用自定义配置类,该类将对您的映射器进行组件扫描
@TestConfiguration
@ComponentScan("com.example.mapper")
public class MappersConfig {
}
然后在您的SpringBootTest#classes
中使用它。例如
@SpringBootTest(classes = {SomeService.class,MappersConfig.class})
class SomeServiceTest {
...
}