Mapstruct:如何映射层次结构,其中子对象是列表并且具有列表属性

发布于 2025-01-12 00:01:10 字数 2170 浏览 5 评论 0原文

我有一个场景,需要从 DTO 对象映射到域对象。

我已经简化了下面的场景

class TopLevel {
    private String attr1;
    private String attr2;
    private List<SecondLevel> secondLevel = new ArrayList<>();
    
    class SecondLevel {
        private String attr3;
        private JsonNode additionalConfig;
        private List<String> stringList = new ArrayList<>();
        private List<ThirdLevel> thirdLevel = new ArrayList<>();

        class ThirdLevel {
            private String attr4;
            private String attr5;
            private List<String> anotherList = new ArrayList<>();
            
        }  

    }  

}

这需要映射到下面的域结构

class TopLevelDomain {
    private ID guid1; //Generated Guid
    private String attr1;
    private String attr2;
    private List<SecondLevelDomain> secondLevelDomain = new ArrayList<>();
}

class SecondLevelDomain {
    private ID guid1; //From TopLevel Domain
    private ID guid2; //Generated Guid
    private String attr3;
    private String stringListAsString; // List of Strings needs to be converted to string (JSON format)
    private String additionalConfig; //JSON node needs to be converted to String (JSON format)
    private List<ThirdLevelDomain> thirdLevelDomain = new ArrayList<>();
}

class ThirdLevelDomain {
    private ID guid1; //From TopLevel Domain
    private ID guid2; //From SecondLevel Guid
    private ID guid3; //New Guid
    private String attr4;
    private String attr5;
    private String anotherListAsString; // List of Strings needs to be converted to string (JSON format)

}

现在我需要进行qualifiedByName/Named映射来获取第一级的GUID。另外,我还需要其他 2 个子级别的类似 GUID。

@Mapping(source = "topLevel", target = "guid1", qualifiedByName = "mapGuid1")
@Mapping(source = "topLevel", target = "secondLevelDomain", qualifiedByName = "secondLevelDomain")
TopLevelDomain toTopLevel(TopLevel topLevel)

如果我执行类似上面代码的操作,我看不出如何访问第二级属性 attr3、additionalConfig 和 @Mapping 注释中的列表 stringList

另外,如何访问第三级属性 attr4、attr5 和 anotherList。我需要直接映射字符串矩阵,分配 guid 并为字符串和 JSONNode 列表进行一些自定义映射

I have a scenario where I need to map from a DTO object to a Domain objects.

I have simplified the scenario below

class TopLevel {
    private String attr1;
    private String attr2;
    private List<SecondLevel> secondLevel = new ArrayList<>();
    
    class SecondLevel {
        private String attr3;
        private JsonNode additionalConfig;
        private List<String> stringList = new ArrayList<>();
        private List<ThirdLevel> thirdLevel = new ArrayList<>();

        class ThirdLevel {
            private String attr4;
            private String attr5;
            private List<String> anotherList = new ArrayList<>();
            
        }  

    }  

}

This needs to be mapped to the domain structure below

class TopLevelDomain {
    private ID guid1; //Generated Guid
    private String attr1;
    private String attr2;
    private List<SecondLevelDomain> secondLevelDomain = new ArrayList<>();
}

class SecondLevelDomain {
    private ID guid1; //From TopLevel Domain
    private ID guid2; //Generated Guid
    private String attr3;
    private String stringListAsString; // List of Strings needs to be converted to string (JSON format)
    private String additionalConfig; //JSON node needs to be converted to String (JSON format)
    private List<ThirdLevelDomain> thirdLevelDomain = new ArrayList<>();
}

class ThirdLevelDomain {
    private ID guid1; //From TopLevel Domain
    private ID guid2; //From SecondLevel Guid
    private ID guid3; //New Guid
    private String attr4;
    private String attr5;
    private String anotherListAsString; // List of Strings needs to be converted to string (JSON format)

}

Now I need to do a qualifiedByName/Named mapping to get the GUID for the first level. Also I need similar GUID for the other 2 child levels as well.

@Mapping(source = "topLevel", target = "guid1", qualifiedByName = "mapGuid1")
@Mapping(source = "topLevel", target = "secondLevelDomain", qualifiedByName = "secondLevelDomain")
TopLevelDomain toTopLevel(TopLevel topLevel)

If I do something like the above code, I see no way how I can access the secondlevel attributes attr3, additionalConfig and the List stringList in the @Mapping annotation

Also how do I access the thirdlevel attributes attr4, attr5 and anotherList. I need to to direct mapping for the string mattributes, assign the guids and do some custom mapping for the List of String and JSONNodes

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(1

世界等同你 2025-01-19 00:01:10

您想要在这里做两件事。

  1. 添加额外的映射方法。 Mapstruct 将使用用户定义的映射方法来生成新的映射方法。
  2. 使用@AfterMapping 传递生成的GUID。
// custom mapping annotations
TopLevelDomain toTopLevel( TopLevel topLevel );

// custom mapping annotations
SecondLevelDomain toSecondLevel( TopLevel.SecondLevel secondLevel );

// custom mapping annotations
ThirdLevelDomain toThirdLevel( TopLevel.SecondLevel.ThirdLevel thirdLevel );

// custom mapping methods

@AfterMapping
default void handleGuidTransfer( TopLevelDomain topLevel ){
    for ( SecondLevelDomain secondLevel: topLevel.getSecondLevelDomain() ) {
        secondLevel.setGuid1( topLevel.getGuid1() );
        for ( ThirdLevelDomain thirdLevel: secondLevel.getThirdLevelDomain() ) {
            thirdLevel.setGuid1( topLevel.getGuid1() );
            thirdLevel.setGuid2( secondLevel.getGuid2() );
        }
    }
}

There are 2 things that you want to do here.

  1. Add additional mapping methods. Mapstruct will use user-defined mapping methods over generating new ones.
  2. Use @AfterMapping to pass on the generated GUID's.
// custom mapping annotations
TopLevelDomain toTopLevel( TopLevel topLevel );

// custom mapping annotations
SecondLevelDomain toSecondLevel( TopLevel.SecondLevel secondLevel );

// custom mapping annotations
ThirdLevelDomain toThirdLevel( TopLevel.SecondLevel.ThirdLevel thirdLevel );

// custom mapping methods

@AfterMapping
default void handleGuidTransfer( TopLevelDomain topLevel ){
    for ( SecondLevelDomain secondLevel: topLevel.getSecondLevelDomain() ) {
        secondLevel.setGuid1( topLevel.getGuid1() );
        for ( ThirdLevelDomain thirdLevel: secondLevel.getThirdLevelDomain() ) {
            thirdLevel.setGuid1( topLevel.getGuid1() );
            thirdLevel.setGuid2( secondLevel.getGuid2() );
        }
    }
}

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文