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

MapStruct使用映射对象作为入参生成代码抛UnsupportedOperationException问题

问题根因
  • 你用到的PredictionRequest和Destination都是Protobuf生成的类,MapStruct内置了Protobuf类型的专属映射逻辑,默认会自动同步两个Protobuf对象的unknownFields以及allFields集合
  • Protobuf生成的getAllFields()方法返回的是不可变Map,不支持putAll操作,所以执行时直接抛出UnsupportedOperationException
  • 当传入非映射生成的对象时,MapStruct识别不到对应Protobuf字段的匹配逻辑,就不会生成这段同步代码,因此不会报错
解决方案

方案1:针对当前Mapper方法单独忽略系统字段

直接在PredictionMapper的map方法上追加两个忽略字段的注解即可,改完重新编译后生成的代码就只会保留你需要的setDestination逻辑:

@Mapping(source = "request.idOrder", target = "referenceId")
@Mapping(source = "request.orderDateUTC", target = "expeditionDate")
@Mapping(source = "protoDestination", target = "destination")
@Mapping(source = "notDeliverableLocalDates", target = "notDeliverableLocalDatesList")
// 追加以下两行,忽略Protobuf自动同步的系统字段
@Mapping(target = "unknownFields", ignore = true)
@Mapping(target = "allFields", ignore = true)
PredictionRequest map(Request request, List<String> notDeliverableLocalDates, Destination protoDestination);

方案2:全局关闭Protobuf字段自动同步逻辑

如果项目里多处都有同类问题,可以全局关闭MapStruct的Protobuf自动字段同步配置,无需每个Mapper单独配置,在maven-compiler-plugin编译参数中添加以下配置即可:

<plugin>
  <groupId>org.apache.maven.plugins</groupId>
  <artifactId>maven-compiler-plugin</artifactId>
  <version>3.8.1</version>
  <configuration>
    <source>11</source>
    <target>11</target>
    <annotationProcessorPaths>
      <path>
        <groupId>org.mapstruct</groupId>
        <artifactId>mapstruct-processor</artifactId>
        <version>你的MapStruct版本号</version>
      </path>
    </annotationProcessorPaths>
    <compilerArgs>
      <!-- 全局关闭Protobuf自动同步字段逻辑 -->
      <arg>-Amapstruct.protobuf.auto-configure-fields=false</arg>
    </compilerArgs>
  </configuration>
</plugin>

方案3:严格控制只映射指定字段

如果需要完全避免MapStruct自动生成未明确声明的映射逻辑,可以给方法加上@BeanMapping(ignoreByDefault = true),只有你标注的@Mapping规则才会生效:

@BeanMapping(ignoreByDefault = true)
@Mapping(source = "request.idOrder", target = "referenceId")
@Mapping(source = "request.orderDateUTC", target = "expeditionDate")
@Mapping(source = "protoDestination", target = "destination")
@Mapping(source = "notDeliverableLocalDates", target = "notDeliverableLocalDatesList")
PredictionRequest map(Request request, List<String> notDeliverableLocalDates, Destination protoDestination);

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.09.30 19:39:03