【问题标题】:Exclude custom deserializer with jackson使用杰克逊排除自定义解串器
【发布时间】:2015-08-18 16:06:25
【问题描述】:

在我的 pojo 类中,我配置了一个带有注释的 CustomDeserializer

@JsonDeserialize(using = CustomDeserializer.class)
class Myclass {
     private String A;
     @JsonIgnore
     private String B;
     @JsonIgnore
     private String C;
     private String D;
     ...
     private String Z;

     /*getters and setters*/
}

CustomDeserializer,我只想管理一些字段,其余的留给Jackson 管理。

CustomDeserializer.java

public class CustomDeserializer extends StdDeserializer<Myclass > {

    private static final long serialVersionUID = 4781685606089836048L;

    public CustomDeserializer() {
        super(Myclass.class);
    }

    @Override
    public Myclass deserialize(JsonParser jp, DeserializationContext ctxt) throws IOException, IllegalResponseException {

        ObjectMapper mapper = (ObjectMapper) jp.getCodec();
        ObjectNode root = (ObjectNode) mapper.readTree(jp);

        Myclass myClass =  mapper.readValue(root.toString(), Myclass.class);

        //--- HERE MANAGE FIELD B ---
        myClass.setB(myNewB);
        //--- HERE MANAGE FIELD C ---
        myClass.setC(myNewC);

        return myClass;
    }
}

这样我会因为下面的行而陷入无限循环:

mapper.readValue(root.toString(), Myclass.class);

有没有办法在使用 Jackson 时设置默认行为,以便我可以排除我的 CustomDeserializer?

【问题讨论】:

  • 你的意思是你只想要一个默认的反序列化?
  • 简而言之,我想使用 CustomDeserializer 作为我的默认反序列化器,并在 CustomDeserializer 内部使用杰克逊默认反序列化器
  • 好的,请看一下我建议的答案,可能对你有用

标签: java jackson deserialization


【解决方案1】:

问题是您需要一个完全构造的默认反序列化器;这需要构建一个,然后您的反序列化器可以访问它。 DeserializationContext 不是您应该创建或更改的东西;由ObjectMapper提供。

为了满足您的要求,您可以先写BeanDeserializerModifier 并通过SimpleModule 注册。

下面的例子应该可以工作:

public class CustomDeserializer extends StdDeserializer<Myclass> implements ResolvableDeserializer
{
  private static final long serialVersionUID = 7923585097068641765L;

  private final JsonDeserializer<?> defaultDeserializer;

  public CustomDeserializer (JsonDeserializer<?> defaultDeserializer)
  {
    super(Myclass.class);
    this.defaultDeserializer = defaultDeserializer;
  }

  @Override public Myclass deserialize(JsonParser jp, DeserializationContext ctxt)
      throws IOException, JsonProcessingException
  {
    Myclass deserializedMyclass = (Myclass) defaultDeserializer.deserialize(jp, ctxt);

    // custom logic

    return deserializedMyclass;
  }

  // You have to implement ResolvableDeserializer when modifying BeanDeserializer
  // otherwise deserializing throws JsonMappingException
  @Override public void resolve(DeserializationContext ctxt) throws JsonMappingException
  {
    ((ResolvableDeserializer) defaultDeserializer).resolve(ctxt);
  }

  public static void main(String[] args) throws JsonParseException, JsonMappingException, IOException
  {
    SimpleModule module = new SimpleModule();
    //Writing a new BeanDeserializerModifier 
    module.setDeserializerModifier(new BeanDeserializerModifier()
    {
      @Override public JsonDeserializer<?> modifyDeserializer(DeserializationConfig config, BeanDescription beanDesc, JsonDeserializer<?> deserializer)
      {
        if (beanDesc.getBeanClass() == Myclass.class)
          return new CustomDeserializer(deserializer);
        return deserializer;
      }
    });

    //register the BeanDeserializerModifier via SimpleModule
    ObjectMapper mapper = new ObjectMapper();
    mapper.registerModule(module);
    Myclass myclass = mapper.readValue(new File("d:\\test.json"), Myclass.class);
  }
}

【讨论】:

  • 自定义反序列化器这里需要默认构造函数吗?如何构造默认的反序列化器?
猜你喜欢
  • 2016-04-26
  • 2019-10-24
  • 2021-05-31
  • 1970-01-01
  • 2014-10-12
  • 2019-05-25
  • 2013-02-21
  • 1970-01-01
  • 2014-01-31
相关资源
最近更新 更多