jackson中自定义处理序列化和反序列化

Posted zhao1949

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了jackson中自定义处理序列化和反序列化相关的知识,希望对你有一定的参考价值。

http://jackyrong.iteye.com/blog/2005323

**********************************************

对于一直用gson的人来说,如果单独用jackson,真是麻烦了,但还是得小结下了:
先来看下如何自定义把某个对象序列化为json:

先是对象:
Java代码 

    public class User {  
        public int id;  
        public String name;  
    }  
    public class Item {  
        public int id;  
        public String itemName;  
        public User owner;  
    }  

JACKSON一般的使用很容易,如;

Item myItem = new Item(1, "theItem", new User(2, "theUser"));
String serialized = new ObjectMapper().writeValueAsString(myItem); 

结果为:

{
    "id": 1,
    "itemName": "theItem",
    "owner": {
        "id": 2,
        "name": "theUser"
    }
} 

如果要输出为如下的样子,比如;

{
    "id": 25,
    "itemName": "FEDUfRgS",
    "owner": 15
} 

  则要自定义了,要继承JsonSerializer类,如下:

    public class ItemSerializer extends JsonSerializer<Item> {  
        @Override  
        public void serialize(Item value, JsonGenerator jgen, SerializerProvider provider)   
          throws IOException, JsonProcessingException {  
            jgen.writeStartObject();  
            jgen.writeNumberField("id", value.id);  
            jgen.writeStringField("itemName", value.itemName);  
            jgen.writeNumberField("owner", value.owner.id);  
            jgen.writeEndObject();  
        }  
    }  

然后

    Item myItem = new Item(1, "theItem", new User(2, "theUser"));  
    ObjectMapper mapper = new ObjectMapper();  
       
    SimpleModule module = new SimpleModule();  
    module.addSerializer(Item.class, new ItemSerializer());  
    mapper.registerModule(module);  
       
    String serialized = mapper.writeValueAsString(myItem);  

看,相当复杂,然后看有无办法简单点,其实是有的哦;方法为:

@JsonSerialize(using = ItemSerializer.class)  
public class Item {  
    ...  
} 

就是使用注解@JsonSerialize,然后:

    Item myItem = new Item(1, "theItem", new User(2, "theUser"));  
    String serialized = new ObjectMapper().writeValueAsString(myItem);  

  接下来看如何反序列化了,
同样,要反序列化的两个pojo为:

    public class User {  
        public int id;  
        public String name;  
    }  
    public class Item {  
        public int id;  
        public String itemName;  
        public User owner;  
    }  

反序列化代码为:

Item itemWithOwner = new ObjectMapper().readValue(json, Item.class); 

如果要自定义反序列化,比如要反序列化的JSON为;

{
    "id": 1,
    "itemName": "theItem",
    "owner": 2
} 

  则上面这样会报错:
com.fasterxml.jackson.databind.exc.UnrecognizedPropertyException:
Unrecognized field "createdBy" (class org.baeldung.jackson.dtos.Item),
not marked as ignorable (3 known properties: "id", "owner", "itemName"])
at [Source: [email protected]; line: 1, column: 43]
(through reference chain: org.baeldung.jackson.dtos.Item["createdBy"])

代码:

    public class ItemDeserializer extends JsonDeserializer<Item> {  
       
        @Override  
        public Item deserialize(JsonParser jp, DeserializationContext ctxt)   
          throws IOException, JsonProcessingException {  
            JsonNode node = jp.getCodec().readTree(jp);  
            int id = (Integer) ((IntNode) node.get("id")).numberValue();  
            String itemName = node.get("itemName").asText();  
            int userId = (Integer) ((IntNode) node.get("id")).numberValue();  
       
            return new Item(id, itemName, new User(userId, null));  
        }  
    }  
      
    ObjectMapper mapper = new ObjectMapper();  
    SimpleModule module = new SimpleModule();  
    module.addDeserializer(Item.class, new ItemDeserializer());  
    mapper.registerModule(module);  
       
    Item readValue = mapper.readValue(json, Item.class);  

也可以用注解:

@JsonDeserialize(using = ItemDeserializer.class)
public class Item {
    ...
} 

 

以上是关于jackson中自定义处理序列化和反序列化的主要内容,如果未能解决你的问题,请参考以下文章

MessagePack Java Jackson Dataformat - 列表(List)的序列化和反序列化

一文详解JackSon配置信息

com.fasterxml.jackson包序列化json对象和反序列化

Spring Boot中的JSON技术

Jackson序列化(8)— 支持泛型的反序列化

Jackson关于Boolean类型反序列化问题