使用MapStruct。例如:
class Dto {
DtoA a;
DtoB b;
}
class DtoA {
Long id;
//...
}
class DtoB {
Long id;
//...
}
class Entity {
AB ab;
}
如何将DtoA
和DtoB
映射到AB?
我尝试过:
public abstract Entity toEntity(Dto dto);
@Mappings({
@Mapping(source = "a", target = "ab.a"),
@Mapping(source = "b", target = "ab.b")
)}
public abstract AB toABEntity(DtoA a, DtoB b);
已经生成了所有代码*,未调用方法toABEntity
。
*很糟糕,因为它先设置a
,然后再设置b
会创建ab
的新实例,因此a
丢失了。
答案 0 :(得分:3)
据我了解,您想将Entity
映射到Dto
并将两个字段Dto.a
和Dto.b
合并到一个字段Entity.ab
中。
通常,当您尝试这样做时:
@Mapper
public interface TestMapper {
@Mappings({
@Mapping(source = "a.id", target = "ab.aId", qualifiedByName = "toAB"),
@Mapping(source = "b.id", target = "ab.bId", qualifiedByName = "toAB"),
})
Entity toEntity(Dto dto);
}
对于每个在ab
内具有目标属性的@Mapping
,生成的映射器将覆盖ab
实例。显然,这是一个错误,并且在MapStructs GitHub上有一张票:https://github.com/mapstruct/mapstruct/issues/1148
但是有一种解决方法:
@Mapper
public interface TestMapper {
@Mappings({
@Mapping(source = "dto", target = "ab", qualifiedByName = "toAB"),
})
Entity toEntity(Dto dto);
@Mappings({
@Mapping(target = "aId", source = "a.id"),
@Mapping(target = "bId", source = "b.id"),
})
AB toAB(Dto dto);
}
我认为AB
类是:
class AB {
public Long aId;
public Long bId;
}
生成的映射器代码:
public class TestMapperImpl implements TestMapper {
@Override
public Entity toEntity(Dto dto) {
if ( dto == null ) {
return null;
}
Entity entity = new Entity();
entity.ab = toAB( dto );
return entity;
}
@Override
public AB toAB(Dto dto) {
if ( dto == null ) {
return null;
}
AB aB = new AB();
Long id = dtoBId( dto );
if ( id != null ) {
aB.bId = id;
}
Long id1 = dtoAId( dto );
if ( id1 != null ) {
aB.aId = id1;
}
return aB;
}
private Long dtoBId(Dto dto) {
if ( dto == null ) {
return null;
}
DtoB b = dto.b;
if ( b == null ) {
return null;
}
Long id = b.id;
if ( id == null ) {
return null;
}
return id;
}
private Long dtoAId(Dto dto) {
if ( dto == null ) {
return null;
}
DtoA a = dto.a;
if ( a == null ) {
return null;
}
Long id = a.id;
if ( id == null ) {
return null;
}
return id;
}
}