使用 MapStruct 框架,您如何将多个字段映射到单个字段(基于自定义逻辑),同时仍将其他字段一对一映射?

这是一个简单的例子来说明我的意思:

public class Source {
    private String firstname;               
    private String surname;  
    // other fields eg:
    private String address; 
    private int age;
    private int favoriteNumber;
}
public class Target {
    private String fullname; // Sould be firstname + surname
    // other fields eg:
    private String address; 
    private int age;
    private int favoriteNumber;
}

我知道可以使用表达式:

@Mapping(target = "fullname", expression = "java(el.getFirstname() + el.getSurname())")

但是在我的特殊用例中,在这个例子中没有描述,我需要使用一些外部库来合并/映射两个字段,这对于表达式是不可行的。

有没有办法在没有表达式的情况下实现合并两个字段?

#1楼 票数:1 已采纳

您可以使用@AfterMapping 注释

https://mapstruct.org/documentation/stable/reference/html/#customizing-mappings-with-before-and-after

你想用抽象类替换你的接口,然后

    @AfterMapping
    void customMapping(@MappingTarget Target target, Source source) {
        // any custom logic
    }

#2楼 票数:0

您声称在表达式中调用外部库是不可行的。 这可能不是真的,这取决于您调用的库的性质和正在使用的框架。

静态方法

如果被调用的方法是类上的静态方法,则可以直接在@Mappingexpression注释元素中@Mapping 为了避免必须完全限定被调用的类,可以使用@Mapperimports元素。

@Mapper(imports = ExternalLibrary.class)
public interface SourceToTargetMapper {
    @Mapping(target = "fullname",
            expression = "java(ExternalLibrary.toFullName(s.getFirstname(), s.getSurname()))")
    Target map(Source s);
}

Spring 框架 bean

如果库方法是Spring bean 上的方法,可以使用 Spring 组件模型将映射器制作成 bean,将包含库方法的 Spring bean 注入映射器:

@Mapper(componentModel = "spring")
public static abstract class SourceToTargetMapper {
    @Autowired
    ExternalLibrary externalLibrary;

    @Mapping(target = "fullname",
            expression = "java(externalLibrary.toFullName(s.getFirstname(), s.getSurname()))")
    abstract Target map(Source s);
}

要使用此映射器,请将其作为 Spring bean 注入,并在 bean 上调用映射方法:

@Component
public class Example {
  @Autowired
  private SourceToTargetMapper mapper;

  public void demonstrate(Source s) {
    System.out.println(mapper.map(s));
  }
}

我没有测试它自己,但我想这注射的方式将与其他工作组件模型由MapStruct支持( cdijsr330 )。

#3楼 票数:0

一种方法是添加从Source对象到合并值的自定义映射方法,然后将合并字段的源声明为整个源对象:

interface CustomMappingMethodMapper {
    @Mapping(target = "fullname", source = ".")
    Target map(Source source);

    default String getFullName(Source s) {
        return s.getFirstname() + " " + s.getSurname();
    }
}

  ask by anopows translate from so

未解决问题?本站智能推荐:

2回复

将多个字段映射到Mapstruct中的一个?

我需要从开放银行课程映射到我的核心课程。 我正在使用mapstruct 。 我需要将多个枚举字段映射到我的核心类上的一个。 但我认为 mapstruct 不支持映射多个字段。 任何棘手的方法或解决方案? 提前致谢! 这是我来自开放银行的枚举值:public enum Category { TRAN
1回复

Mapstruct将一个字段映射到多个目标字段,反之亦然

我已经提到了使用Mapstruct将多个源字段映射到相同类型的目标字段的问题,但这没有帮助 我的其余资源类如下 我的实体类是Source,如下所示: 我想在Source Map类中使用emailAdddress或device或mobileNumbers映射Source类中的地址,我尝
3回复

MapStruct:对象的映射列表,当对象从两个对象映射时

假设我有这样的映射: 现在我需要将 ChildDto 列表映射到 Child 列表,但它们都具有相同的父级。 我希望做这样的事情: 但它不起作用。 有机会做到吗?
3回复

如何使用mapstruct仅映射选定的字段

如何仅使用 mapStruct 映射选定的字段并返回 nm 作为响应。 例如: 现在我可以使用以下方法映射它们: 现在, returnObject将包含 location ,其中包含street, unit and postCode 。 但是,我只想用 returnObject.location 公
1回复

如何将Mapstruct与AdHocSetter一起使用

我正在尝试将 MapStruct 应用于 DDD。 我用这样的临时设置器创建了我的实体: 我有一个EmployeeDto将数据发送到前端 API: 所以,我正在尝试使用 MapStruct 进行映射,但由于我的临时设置器而无法正常工作。 我该如何解决这个问题?
3回复

MapStruct:如何将所有属性映射到列表的第一个元素?

我需要一个映射来实现这一点: 但是这种语法不起作用(顺便说一句:这适用于 Spring Bean 包装器)。 像这样的解决方案只是一个半熟的解决方案: 这仅适用于一个属性,因为它总是为每个属性创建一个新列表。 我不需要将每个属性映射到新列表的第一个元素。 该列表必须重复使用,但我不知道这是如何工作的
1回复

Mapstruct:有条件地映射字段或忽略

我有一个这样的课程: 只有当标志isFailed为真时,我才想将failedCourses List 从failedCourses映射到 Student,否则忽略该字段,但不使用接口中的默认实现。 mapstruct 中是否有任何注释/参数可以帮助我? 我试过使用expression但不能让它工作
1回复

Mapstruct:根据其字段之一的值忽略集合的某些元素

我有这些豆子: 我也有一些用于这些 bean 的 DTO (请注意,AddressDto 类缺少deleted字段) 我正在使用 Mapstruct 将这些 bean 映射到它们的 DTO。 映射器是这样的: 现在,在映射中,我想忽略其deleted字段为true的 Address 实例。 有没有