【Java】将JSON转换为Java,将Java转换为JSON 〜使用GSON和Jackson的方法〜
简而言之,只需要一种选择。
在使用Java进行Web API时,常常使用的JSON→Java、Java→JSON的方法进行总结。
此外,关于如何将JSON进行HTTP POST或HTTP GET的方法将在下一篇文章中进行总结。
【本稿】JavaでJSONを扱う方法についてまとめます
JSONをJavaに変換(デシリアライズ)、JavaをJSONに変換(シリアライズ)するやり方は2通り説明します
ライブラリにGSONを使うやり方
ライブラリにJacksonを使うやり方
【次稿】JavaでHTTP通信でJSONをPOSTしたり、GETしたりする方法についてもまとめます
JavaでHTTP通信をするやり方も2通り説明します
OkHttp3を使ったやり方
Java標準パッケージであるHttpUrlConnectionを使ったやり方
以JSON为基础思考的最短路径
在调用外部API时,如果已经存在要解析的JSON字符串,则考虑使用最短路径。可以利用自动生成模型类的网站,只要有JSON字符串即可(如果有JSON schema更好)。
{
"person": {
"firstName": "John",
"lastName": "Doe",
"address": "NewYork",
"pets": [
{"type": "Dog", "name": "Jolly"},
{"type": "Cat", "name": "Grizabella"},
{"type": "Fish", "name": "Nimo"}
]
}
}
GSON和Jackson
在Java中进行JSON操作时,常常使用两个库,即GSON和Jackson。
由于无法一概而论哪个更好,因此需要对两者进行说明。
GSON编程库
使用GSON将JSON映射到Java中。
首先从GSON开始。考虑到JSON,也就是从原始的JSON字符串中创建一个Java解析器,我们可以尝试使用jsonschema2pojo,这样比较方便。
本章的源代码在这里:
https://github.com/riversun/java-json-gson-jackson-http/tree/master/src/main/java/com/example/gson
GSON的库依赖关系
GSON的库指定方法如下所示
■ GSON的最新库(maven仓库)
https://mvnrepository.com/artifact/com.google.code.gson/gson
■ 一个使用GSON库的Maven配置示例
<dependency>
<groupId>com.google.code.gson</groupId>
<artifactId>gson</artifactId>
<version>2.8.5</version>
</dependency>
■ GSON的gradle配置示例
compile 'com.google.code.gson:gson:2.8.5'
使用jsonschema2pojo自动生成模型类(POJO)。
请访问以下网站,在上方粘贴JSON内容:
http://www.jsonschema2pojo.org/
如果对外部网站有抵抗,也可以使用库来自行完成。
在网站上进行以下设置,当点击“Zip”时,将会自动生成模型类。
包:com.example.gson(包名,可以是任何名字,但源代码将自动生成与该包名相关的代码)
类名:Model(POJO最顶层的类名)
目标语言:Java
源类型:JSON(从JSON字符串中推测出模型类)
注释风格:Gson(使用GSON进行解析)
☑ 允许额外属性(即使JSON中混有未知属性也可以)
生成一个Zip文件,下载并打开后,会自动生成以下三个Java文件。
(2) 查看自动生成的模型类(POJO)
■ Model.java:顶层类
package com.example.gson;
import com.google.gson.annotations.Expose;
import com.google.gson.annotations.SerializedName;
public class Model {
@SerializedName("person")
@Expose
public Person person;
}
Person.java中的”pets”:[]这样的数组指定会变成一个List。
package com.example.gson;
import java.util.List;
import com.google.gson.annotations.Expose;
import com.google.gson.annotations.SerializedName;
public class Person {
@SerializedName("firstName")
@Expose
public String firstName;
@SerializedName("lastName")
@Expose
public String lastName;
@SerializedName("address")
@Expose
public String address;
@SerializedName("pets")
@Expose
public List<Pet> pets = null;
}
■ 宠物.java
package com.example.gson;
import com.google.gson.annotations.Expose;
import com.google.gson.annotations.SerializedName;
public class Pet {
@SerializedName("type")
@Expose
public String type;
@SerializedName("name")
@Expose
public String name;
}
使用GSON库,将JSON转换为Java代码。
使用GSON将JSON字符串转换为Java模型类,即将JSON从JSON转为Java。关键代码如下:
Gson gson = new Gson();
Model model = gson.fromJson(json, Model.class);
整个代码如下所示
■ GsonJson2Java.java的中文本地化版本
package com.example.gson;
import com.google.gson.Gson;
public class GsonJson2Java {
public static void main(String[] args) {
String json =
"{" +
" \"person\": {" +
" \"firstName\": \"John\"," +
" \"lastName\": \"Doe\"," +
" \"address\": \"NewYork\"," +
" \"pets\": [" +
" {\"type\": \"Dog\", \"name\": \"Jolly\"}," +
" {\"type\": \"Cat\", \"name\": \"Grizabella\"}," +
" {\"type\": \"Fish\", \"name\": \"Nimo\"}" +
" ]" +
" }" +
"}";
Gson gson = new Gson();
Model model = gson.fromJson(json, Model.class);
System.out.println("firstName:" + model.person.firstName);
System.out.println("lastName:" + model.person.lastName);
System.out.println("address:" + model.person.address);
System.out.println("1st pet:" + model.person.pets.get(0).name);
}
}
firstName:John
lastName:Doe
address:NewYork
1st pet:Jolly
使用GSON,在Java和JSON之间进行转换。
现在,我们要用Java来处理JSON了。将Java的模型类(POJO)转换为JSON格式。
Gson gson = new Gson();
String json = gson.toJson(model);
GsonJava2Json.java的中文完全原生解释
package com.example.gson;
import java.util.ArrayList;
import com.google.gson.Gson;
public class GsonJava2Json {
public static void main(String[] args) {
Model model = new Model();
model.person = new Person();
model.person.firstName = "ジョン";
model.person.lastName = "ドゥ";
model.person.address = "ニューヨーク";
model.person.pets = new ArrayList<Pet>();
Pet pet1 = new Pet();
pet1.type = "犬";
pet1.name = "ジョリー";
model.person.pets.add(pet1);
Pet pet2 = new Pet();
pet2.type = "猫";
pet2.name = "グリザベラ";
model.person.pets.add(pet2);
Pet pet3 = new Pet();
pet3.type = "魚";
pet3.name = "ニモ";
model.person.pets.add(pet3);
Gson gson = new Gson();
String json = gson.toJson(model);
System.out.println(json);
}
}
执行此操作后,可以从模型类中导出JSON,输出如下所示。
{"person":{"firstName":"ジョン","lastName":"ドゥ","address":"ニューヨーク","pets":[{"type":"犬","name":"ジョリー"},{"type":"猫","name":"グリザベラ"},{"type":"魚","name":"ニモ"}]}}
使用GSON对JSON进行格式化(Pretty Printing),然后输出。
这样做的话,JSON会以缩进的方式漂亮地格式化出来。
Gson gson2 = new GsonBuilder().setPrettyPrinting().create();
String prettyJson = gson2.toJson(model);
System.out.println(prettyJson);
执行结果
{
"person": {
"firstName": "ジョン",
"lastName": "ドゥ",
"address": "ニューヨーク",
"pets": [
{
"type": "犬",
"name": "ジョリー"
},
{
"type": "猫",
"name": "グリザベラ"
},
{
"type": "魚",
"name": "ニモ"
}
]
}
}
Jackson编辑
– 删除文档中的错误部分。
– 在页面上插入新的图像。
– 重新组织段落和章节以改进流畅度。
– 编辑并修改语法和拼写错误。
Jackson有1.x系列和2.x系列,但使用2.x系列。
使用Jackson将JSON映射到Java
本章的源代码可以在这里找到:https://github.com/riversun/java-json-gson-jackson-http/tree/master/src/main/java/com/example/jackson
Jackson库的依赖关系
Jackson库的指定方法如下所示。
■ 杰克逊的最新库(Maven仓库)
https://mvnrepository.com/artifact/com.fasterxml.jackson.core/jackson-databind
■ Jackson的Maven配置示例
<dependency>
<groupId>com.fasterxml.jackson.core</groupId>
<artifactId>jackson-databind</artifactId>
<version>2.9.8</version>
</dependency>
■ Jackson的gradle配置示例
compile 'com.fasterxml.jackson.core:jackson-databind:2.9.8'
使用jsonschema2pojo自动生成模型类(POJO)
请点击以下链接进入该网站:http://www.jsonschema2pojo.org/,然后将上方的JSON粘贴进去。
在网页上进行以下设置,点击“Zip”即可自动生成模型类。
包名:com.example.jackson(包名,可以是任意的,但是生成的源代码带有该包名)
类名:Model(Pojo的最顶层类名)
目标语言:Java
源类型:JSON(根据JSON字符串本身来推断模型类)
注解风格:Jackson 2.x(使用Jackson 2.x解析器)
☑允许额外的属性(即使JSON中有未知属性也可以)
生成一个Zip文件,下载并打开后,会自动生成以下3个Java文件。
(2) 查看自动生成的模型类(POJO)
■ Model.java是一个顶层类。它通过设置@JsonAnyGetter来接受额外的属性,这是其特点。因此,相比于GSON,它变得更加冗长。
package com.example.jackson;
import java.util.HashMap;
import java.util.Map;
import com.fasterxml.jackson.annotation.JsonAnyGetter;
import com.fasterxml.jackson.annotation.JsonAnySetter;
import com.fasterxml.jackson.annotation.JsonIgnore;
import com.fasterxml.jackson.annotation.JsonInclude;
import com.fasterxml.jackson.annotation.JsonProperty;
import com.fasterxml.jackson.annotation.JsonPropertyOrder;
@JsonInclude(JsonInclude.Include.NON_NULL)
@JsonPropertyOrder({
"person"
})
public class Model {
@JsonProperty("person")
public Person person;
@JsonIgnore
private Map<String, Object> additionalProperties = new HashMap<String, Object>();
@JsonAnyGetter
public Map<String, Object> getAdditionalProperties() {
return this.additionalProperties;
}
@JsonAnySetter
public void setAdditionalProperty(String name, Object value) {
this.additionalProperties.put(name, value);
}
}
■ Person.java中的@JsonPropertyOrder可用于约束出现顺序。被指定为”pets”:[]的数组将被转换为List。
package com.example.jackson;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import com.fasterxml.jackson.annotation.JsonAnyGetter;
import com.fasterxml.jackson.annotation.JsonAnySetter;
import com.fasterxml.jackson.annotation.JsonIgnore;
import com.fasterxml.jackson.annotation.JsonInclude;
import com.fasterxml.jackson.annotation.JsonProperty;
import com.fasterxml.jackson.annotation.JsonPropertyOrder;
@JsonInclude(JsonInclude.Include.NON_NULL)
@JsonPropertyOrder({
"firstName",
"lastName",
"address",
"pets"
})
public class Person {
@JsonProperty("firstName")
public String firstName;
@JsonProperty("lastName")
public String lastName;
@JsonProperty("address")
public String address;
@JsonProperty("pets")
public List<Pet> pets = null;
@JsonIgnore
private Map<String, Object> additionalProperties = new HashMap<String, Object>();
@JsonAnyGetter
public Map<String, Object> getAdditionalProperties() {
return this.additionalProperties;
}
@JsonAnySetter
public void setAdditionalProperty(String name, Object value) {
this.additionalProperties.put(name, value);
}
}
宠物.java
package com.example.jackson;
import java.util.HashMap;
import java.util.Map;
import com.fasterxml.jackson.annotation.JsonAnyGetter;
import com.fasterxml.jackson.annotation.JsonAnySetter;
import com.fasterxml.jackson.annotation.JsonIgnore;
import com.fasterxml.jackson.annotation.JsonInclude;
import com.fasterxml.jackson.annotation.JsonProperty;
import com.fasterxml.jackson.annotation.JsonPropertyOrder;
@JsonInclude(JsonInclude.Include.NON_NULL)
@JsonPropertyOrder({
"type",
"name"
})
public class Pet {
@JsonProperty("type")
public String type;
@JsonProperty("name")
public String name;
@JsonIgnore
private Map<String, Object> additionalProperties = new HashMap<String, Object>();
@JsonAnyGetter
public Map<String, Object> getAdditionalProperties() {
return this.additionalProperties;
}
@JsonAnySetter
public void setAdditionalProperty(String name, Object value) {
this.additionalProperties.put(name, value);
}
}
使用Jackson将JSON转换为Java。
使用Jackson将JSON字符串加载到Java模型类中,实现从JSON到Java的转换的关键代码如下:
ObjectMapper mapper = new ObjectMapper();
Model model = mapper.readValue(json, Model.class);
The entire code would be as follows:
整个代码如下:
■ JacksonJson2Java.java
杰克逊Json2Java.java
package com.example.jackson;
import java.io.IOException;
import com.fasterxml.jackson.core.JsonParseException;
import com.fasterxml.jackson.databind.JsonMappingException;
import com.fasterxml.jackson.databind.ObjectMapper;
public class JacksonJson2Java {
public static void main(String[] args) throws JsonParseException, JsonMappingException, IOException {
String json = "{" +
" \"person\": {" +
" \"firstName\": \"John\"," +
" \"lastName\": \"Doe\"," +
" \"address\": \"NewYork\"," +
" \"pets\": [" +
" {\"type\": \"Dog\", \"name\": \"Jolly\"}," +
" {\"type\": \"Cat\", \"name\": \"Grizabella\"}," +
" {\"type\": \"Fish\", \"name\": \"Nimo\"}" +
" ]" +
" }" +
"}";
ObjectMapper mapper = new ObjectMapper();
Model model = mapper.readValue(json, Model.class);
System.out.println("firstName:" + model.person.firstName);
System.out.println("lastName:" + model.person.lastName);
System.out.println("address:" + model.person.address);
System.out.println("1st pet:" + model.person.pets.get(0).name);
}
}
使用 Jackson,将 Java 转换为 JSON。
现在让我们来介绍一下如何通过Java来处理JSON。我们需要将Java的模型类(POJO)转化为JSON格式。
ObjectMapper mapper = new ObjectMapper();
String json = mapper.writeValueAsString(model);
JacksonJava2Json.java 的中文释义是什么?
package com.example.jackson;
import java.util.ArrayList;
import com.fasterxml.jackson.core.JsonProcessingException;
import com.fasterxml.jackson.databind.ObjectMapper;
public class JacksonJava2Json {
public static void main(String[] args) throws JsonProcessingException {
Model model = new Model();
model.person = new Person();
model.person.firstName = "ジョン";
model.person.lastName = "ドゥ";
model.person.address = "ニューヨーク";
model.person.pets = new ArrayList<Pet>();
Pet pet1 = new Pet();
pet1.type = "犬";
pet1.name = "ジョリー";
model.person.pets.add(pet1);
Pet pet2 = new Pet();
pet2.type = "猫";
pet2.name = "グリザベラ";
model.person.pets.add(pet2);
Pet pet3 = new Pet();
pet3.type = "魚";
pet3.name = "ニモ";
model.person.pets.add(pet3);
ObjectMapper mapper = new ObjectMapper();
String json = mapper.writeValueAsString(model);
System.out.println(json);
}
}
当执行此命令时,能够从模型类中以以下格式输出JSON。
{"person":{"firstName":"ジョン","lastName":"ドゥ","address":"ニューヨーク","pets":[{"type":"犬","name":"ジョリー"},{"type":"猫","name":"グリザベラ"},{"type":"魚","name":"ニモ"}]}}
使用Jackson库将JSON格式化(Pretty Printing)并输出。
按照这样的方式,JSON会被缩进并以漂亮的格式呈现出来。
ObjectMapper mapper2 = new ObjectMapper();
String prettyJson = mapper2.writerWithDefaultPrettyPrinter().writeValueAsString(model);
System.out.println(prettyJson);
运行结果
{
"person" : {
"firstName" : "ジョン",
"lastName" : "ドゥ",
"address" : "ニューヨーク",
"pets" : [ {
"type" : "犬",
"name" : "ジョリー"
}, {
"type" : "猫",
"name" : "グリザベラ"
}, {
"type" : "魚",
"name" : "ニモ"
} ]
}
}
总结
GSONをつかってJSON→Java、Java→JSONをお手軽に実行する方法を説明しました
GSONを使ったソースコードはこちらです
Jacksonの場合も同様に説明しました
Jacksonを使ったソースコードはこちらです
JSONをHTTP通信でPOSTやGETする方法はこちらにまとめました