MapStruct No qualifying bean
同时使用 Lombok 和 MapStruct,编译运行报错:
No qualifying bean of type 'xxx' available: expected at least 1 bean which qualifies as autowire candidate. Dependency annotations: {}
原因:@Mapper
注解不能向容器中注入 bean。
解决: @Mapper
注解填写 componentModel
属性值,如下:
@Mapper(componentModel = MappingConstants.ComponentModel.SPRING)
默认 DEFAULT
不使用任何组件模型,通常通过 org.mapstruct.factory.Mappers.getMapper(Class)
检索实例。
配合 Spring 使用的话应该设置为 SPRING
,这样生成的 mapper 实现类是一个 Spring bean 进而可以通过 @Autowired
注入。
还有其他多种取值例如 CDI、JSR330、JAKARTA 等等,可以查看源码
/**
* Specifies the component model constants to which the generated mapper should adhere.
* It can be used with the annotation {@link Mapper#componentModel()} or {@link MapperConfig#componentModel()}
*
* <p>
* <strong>Example:</strong>
* </p>
* <pre><code class='java'>
* // Spring component model
* @Mapper(componentModel = MappingConstants.ComponentModel.SPRING)
* </code></pre>
*
* @since 1.5.0
*/
public static final class ComponentModel {
private ComponentModel() {
}
/**
* The mapper uses no component model, instances are typically retrieved
* via {@link org.mapstruct.factory.Mappers#getMapper(java.lang.Class)}
*
*/
public static final String DEFAULT = "default";
/**
* The generated mapper is an application-scoped CDI bean and can be retrieved via @Inject.
* The annotations are either from {@code javax} or {@code jakarta}.
* Priority have the {@code javax} annotations.
* In case you want to only use Jakarta then use {@link #JAKARTA_CDI}.
*
* @see #JAKARTA_CDI
*/
public static final String CDI = "cdi";
/**
* The generated mapper is a Spring bean and can be retrieved via @Autowired
*
*/
public static final String SPRING = "spring";
/**
* The generated mapper is annotated with @Named and @Singleton, and can be retrieved via @Inject.
* The annotations are either from {@code javax.inject} or {@code jakarta.inject}.
* Priority have the {@code javax.inject} annotations.
* In case you want to only use Jakarta then use {@link #JAKARTA}.
*
* @see #JAKARTA
*/
public static final String JSR330 = "jsr330";
/**
* The generated mapper is annotated with @Named and @Singleton, and can be retrieved via @Inject.
* The annotations are from {@code jakarta.inject}.
* In case you want to use {@code javax.inject} then use {@link #JSR330}.
*
* @see #JSR330
*/
public static final String JAKARTA = "jakarta";
/**
* The generated mapper is an application-scoped Jakarta CDI bean and can be retrieved via @Inject.
* @see #CDI
*/
public static final String JAKARTA_CDI = "jakarta-cdi";
}
少一些功利主义的追求,多一些不为什么的坚持