[英]Mapstruct: Ignore some elements of a collection based on the value of one of their fields
[英]How to ignore some fields in MapStruct when using the new @SubclassMapping annotation?
使用当前的 1.5.0.Beta2 MapStruct 版本和 JDK 13。
class Wrapper {
private Fruit fruit;
}
abstract class Fruit {
private int weight;
/* ... */
}
class Apple extends Fruit {
/* ... */
}
class Banana extends Fruit {
/* ... */
}
(相应的 1:1 DTO 省略)
@Mapper(uses = {FruitMapper.class})
public interface WrapperMapper {
WrapperDto map(Wrapper wrapper)
}
带有方法签名和注释的抽象Fruit
class 的 MapStruct Mapper
:
@Mapper(subclassExhaustiveStrategy = SubclassExhaustiveStrategy.RUNTIME_EXCEPTION /*...*/)
public interface FruitMapper {
@SubclassMapping(source = Apple.class, target = AppleDto.class)
@SubclassMapping(source = Banana.class, target = BananaDto.class)
FruitDto map(Fruit fruit);
}
以上工作正常,直到需要在引用的抽象 class 上忽略字段(例如Fruit
的weight
)。 将此注释WrapperMapper
map
方法...
@Mapping(target = "fruit.weight", ignore = true)
WrapperDto map(Wrapper wrapper)
...导致The return type FruitDto is an abstract class or interface. Provide a non abstract / non interface result type or a factory method.
The return type FruitDto is an abstract class or interface. Provide a non abstract / non interface result type or a factory method.
编译错误。
有没有办法按照概述跳过 MapStruct 映射中的字段而不会出现此编译错误?
发生的情况是,因为您在 WrapperMapper 上指定了它,所以它不会直接使用 FruitMapper。 相反,WrapperMapper 实现将获得一个新的映射方法,生成到 map 水果。 MapStruct 在此尝试中失败,并为您提供编译错误。
如果您将忽略添加到 FruitMapper,它将继承它到两个子类映射:
@SubclassMapping( source = Apple.class, target = AppleDto.class )
@SubclassMapping( source = Banana.class, target = BananaDto.class )
@Mapping( target = "weight", ignore = true )
FruitDto map( Fruit fruit );
如果您想要一个有权重的映射和一个没有权重的映射,您可以将@org.mapstruct.Named
注释添加到没有权重的映射,然后在 WrappedMapper 中使用它。
像这样:
@Mapper(subclassExhaustiveStrategy = SubclassExhaustiveStrategy.RUNTIME_EXCEPTION /*...*/)
public interface FruitMapper {
@SubclassMapping( source = Apple.class, target = AppleDto.class )
@SubclassMapping( source = Banana.class, target = BananaDto.class )
FruitDto map( Fruit fruit );
@SubclassMapping( source = Apple.class, target = AppleDto.class )
@SubclassMapping( source = Banana.class, target = BananaDto.class )
@Mapping( target = "weight", ignore = true )
@Named( "NoWeights" )
FruitDto map( Fruit fruit );
}
@Mapper(uses = {FruitMapper.class})
public interface WrapperMapper {
@Mapping( target = "fruit", qualifiedByName = "NoWeights" )
WrapperDto map(Wrapper wrapper)
}
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.