Java:使用MapStruct映射DTO层次结构

时间:2020-01-14 05:08:01

标签: mapstruct mapper

我有Pet,Dog和Cat实体类。狗和猫类扩展了宠物。

我还用@JsonSubtype注释了PetDTO,DogDTO和CatDTO,因此Jackson很好地解决了dto的类。

我想使用MapStruct编写一个映射器,该映射器接受PetDTO实体(可以是DogDTO或CatDTO)并返回Dog或Cat。

在这种情况下,对我而言,使用映射库的主要目标是避免使用instanceof编写糟糕的代码。

有什么主意吗?谢谢!

2 个答案:

答案 0 :(得分:1)

当前无法立即使用-请在mapstruct的GitHub:#366 Support for abstract class mapping or classes with base class中查看此票证。您可以尝试将其推向此处,也可以自己贡献此功能。看起来似乎是一个合理的功能。

我想在当前情况下,这是您最好的选择:

@Mapper
public interface PetMapper {

    default PetDTO toPetDto(Pet pet) {
        if (pet instanceof Dog) {
            return toDogDTO((Dog) pet);
        }

        if (pet instanceof Cat) {
            return toCatDTO((Cat) pet);
        }

        throw new IllegalArgumentException("Unknown subtype of Pet");
    }

    default Pet toPetEntity(PetDTO petDTO) {
        if (petDTO instanceof DogDTO) {
            return toDogEntity((DogDTO) petDTO);
        }

        if (petDTO instanceof CatDTO) {
            return toCatEntity((CatDTO) petDTO);
        }

        throw new IllegalArgumentException("Unknown subtype of PetDTO");
    }

    DogDTO toDogDTO(Dog dog);
    Dog toDogEntity(DogDTO dogDTO);

    CatDTO toCatDTO(Cat cat);
    Cat toCatEntity(CatDTO catDTO);
}

答案 1 :(得分:0)

我最终为上述类似案例实现 Mapper 的方式是结合使用 switch 类型、MapStruct Update Existing 和创建 Mapper。

在我的例子中,源对象上的一个属性决定了我们必须生成的子类。 我最初为每个子类型使用了不同的映射器,但是公共映射属性的重复似乎是错误的。所以我想出了以下内容,利用 MapStruct 使用更新映射器的能力来处理常见的父类型属性:

createDocumentList()