You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何通过MapStruct声明式实现基于LegType的Leg到TripLeg映射?

MapStruct声明式实现Leg到TripLeg的动态字段填充

针对你的需求,确实可以通过声明式注解实现根据Leg.type填充TripLeg对应字段的逻辑,无需依赖装饰器的自定义代码,具体方案如下:

方案一:使用@Mapping的expression属性

直接在映射接口中通过expression属性编写条件判断,根据Leg.type的值选择对应的子映射方法,其余字段置为null:

@Mapper
public interface LegMapper {
    LegMapper INSTANCE = Mappers.getMapper(LegMapper.class);

    @Mapping(target = "timedLeg", expression = "java(leg.getType() == LegType.TIMED ? mapToTimedLeg(leg) : null)")
    @Mapping(target = "transferLeg", expression = "java(leg.getType() == LegType.TRANSFER ? mapToTransferLeg(leg) : null)")
    @Mapping(target = "continuousLeg", expression = "java(leg.getType() == LegType.CONTINUOUS ? mapToContinuousLeg(leg) : null)")
    TripLeg legToTripLeg(Leg leg);

    // MapStruct自动生成Leg到各子Leg类型的映射逻辑,可按需添加@Mapping自定义字段映射
    TimedLeg mapToTimedLeg(Leg leg);
    TransferLeg mapToTransferLeg(Leg leg);
    ContinuousLeg mapToContinuousLeg(Leg leg);
}

说明:

  • 所有映射规则通过注解声明,属于纯声明式实现,无需额外装饰器类;
  • 子映射方法可由MapStruct自动生成,若需要自定义字段映射,直接在对应方法上添加@Mapping注解即可。

方案二:结合默认方法封装判断逻辑(更易维护)

如果觉得expression中的重复代码不够优雅,可以在映射接口中定义默认方法封装判断逻辑,再通过@Named和qualifiedByName关联映射规则:

@Mapper
public interface LegMapper {
    LegMapper INSTANCE = Mappers.getMapper(LegMapper.class);

    @Mapping(target = "timedLeg", source = "leg", qualifiedByName = "timedLegCondition")
    @Mapping(target = "transferLeg", source = "leg", qualifiedByName = "transferLegCondition")
    @Mapping(target = "continuousLeg", source = "leg", qualifiedByName = "continuousLegCondition")
    TripLeg legToTripLeg(Leg leg);

    TimedLeg mapToTimedLeg(Leg leg);
    TransferLeg mapToTransferLeg(Leg leg);
    ContinuousLeg mapToContinuousLeg(Leg leg);

    @Named("timedLegCondition")
    default TimedLeg mapTimedLegConditionally(Leg leg) {
        return leg.getType() == LegType.TIMED ? mapToTimedLeg(leg) : null;
    }

    @Named("transferLegCondition")
    default TransferLeg mapTransferLegConditionally(Leg leg) {
        return leg.getType() == LegType.TRANSFER ? mapToTransferLeg(leg) : null;
    }

    @Named("continuousLegCondition")
    default ContinuousLeg mapContinuousLegConditionally(Leg leg) {
        return leg.getType() == LegType.CONTINUOUS ? mapToContinuousLeg(leg) : null;
    }
}

说明:

  • 逻辑封装在默认方法中,映射规则仍通过注解声明,属于声明式实现范畴;
  • 后续修改判断逻辑时,只需调整对应默认方法,映射接口的注解结构无需变动,更易维护。

以上两种方案均无需使用装饰器,完全基于MapStruct的原生注解特性实现需求,符合声明式编程的要求。

内容的提问来源于stack exchange,提问作者jspetrak

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.26 10:02:31