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

如何用Jackson反序列化派生类?自动生成类无注解场景

解决方案:在无注解和类型信息的情况下反序列化子类实例

当然可以解决这个问题!因为你无法修改自动生成的类添加@JsonSubType等注解,也没法在输入的序列化内容里加入类型标识,我们可以通过Jackson的自定义反序列化器或者字段推断逻辑来处理,具体分两种场景说明:

场景1:所有ClauseType实例都应反序列化为DataMonitoringClauseType

如果你的输入中clauses列表里的元素全部是DataMonitoringClauseType的序列化结果,那可以直接强制将ClauseType类型的反序列化指向DataMonitoringClauseType:

步骤1:自定义反序列化器

创建一个针对ClauseType的反序列化器,直接把JSON解析为DataMonitoringClauseType实例:

import com.fasterxml.jackson.core.JsonParser;
import com.fasterxml.jackson.databind.DeserializationContext;
import com.fasterxml.jackson.databind.deser.std.StdDeserializer;
import java.io.IOException;

public class ClauseTypeDeserializer extends StdDeserializer<ClauseType> {
    public ClauseTypeDeserializer() {
        super(ClauseType.class);
    }

    @Override
    public ClauseType deserialize(JsonParser p, DeserializationContext ctxt) throws IOException {
        // 直接将JSON解析为DataMonitoringClauseType
        return p.readValueAs(DataMonitoringClauseType.class);
    }
}

步骤2:注册反序列化器到ObjectMapper

把自定义的反序列化器注册到你的ObjectMapper实例中:

ObjectMapper mapper = new ObjectMapper();
SimpleModule customModule = new SimpleModule();
customModule.addDeserializer(ClauseType.class, new ClauseTypeDeserializer());
mapper.registerModule(customModule);

// 现在反序列化RootClass时,clauses里的元素会是DataMonitoringClauseType实例
RootClass root = mapper.readValue(jsonInput, RootClass.class);

场景2:clauses列表中有多种ClauseType子类(需字段推断)

如果列表里可能存在不同的ClauseType子类,你可以通过JSON中的特定字段来推断具体类型(比如某个字段的存在或特定值),修改反序列化器的逻辑即可:

@Override
public ClauseType deserialize(JsonParser p, DeserializationContext ctxt) throws IOException {
    JsonNode node = p.getCodec().readTree(p);
    
    // 假设DataMonitoringClauseType对应的JSON有"monitoringConfig"字段
    if (node.has("monitoringConfig")) {
        return p.getCodec().treeToValue(node, DataMonitoringClauseType.class);
    }
    // 其他子类的判断逻辑...
    else {
        // 默认返回ClauseType实例
        return p.getCodec().treeToValue(node, ClauseType.class);
    }
}

为什么registerSubtypes没用?

你之前尝试的mapper.registerSubtypes(DataMonitoringClauseType.class)之所以无效,是因为Jackson的registerSubtypes需要配合@JsonTypeInfo注解使用——这个注解告诉Jackson如何识别不同的子类(比如通过某个字段、类型名称等)。由于你的自动生成类没有添加这个注解,Jackson无法得知应该如何将JSON映射到对应的子类,所以单独注册子类是不起作用的。

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.05.27 09:54:21