问题
I have a UI
which sends this object -
com.google.api.services.compute.model.Network
in JSON
format as part of a HTTP
request. I need to deserialize this object to the Java
object. How do I do that? I wrote a simple POJO
like below to mimic the behaviour.
package com.techm.studio.client;
import java.io.IOException;
import com.google.api.services.compute.model.Network;
import com.google.api.services.compute.model.NetworkRoutingConfig;
import com.google.gson.Gson;
import com.google.gson.GsonBuilder;
public class JSONTest {
public static void main(String[] args) throws IOException {
Network network = new Network();
network.setName("k-network");
network.setAutoCreateSubnetworks(false);
network.setDescription("My test network on Google Cloud");
network.setIPv4Range("10.0.0.0/16");
network.setRoutingConfig(new NetworkRoutingConfig().setRoutingMode("REGIONAL"));
String nwkJsonString = new GsonBuilder().setPrettyPrinting().create().toJson(network);
System.out.println("JSON String from POJO ==>\n" + nwkJsonString);
Network netwrkOut = new Gson().fromJson(nwkJsonString, Network.class);
System.out.println(netwrkOut.toPrettyString());
}
}
And this is the output I get.
JSON String from POJO ==>
{
"IPv4Range": "10.0.0.0/16",
"autoCreateSubnetworks": false,
"description": "My test network on Google Cloud",
"name": "k-network",
"routingConfig": {
"routingMode": "REGIONAL"
}
}
Exception in thread "main" java.lang.IllegalArgumentException: Can not set com.google.api.services.compute.model.NetworkRoutingConfig field com.google.api.services.compute.model.Network.routingConfig to com.google.gson.internal.LinkedTreeMap
at sun.reflect.UnsafeFieldAccessorImpl.throwSetIllegalArgumentException(UnsafeFieldAccessorImpl.java:167)
at sun.reflect.UnsafeFieldAccessorImpl.throwSetIllegalArgumentException(UnsafeFieldAccessorImpl.java:171)
at sun.reflect.UnsafeObjectFieldAccessorImpl.set(UnsafeObjectFieldAccessorImpl.java:81)
at java.lang.reflect.Field.set(Field.java:764)
at com.google.api.client.util.FieldInfo.setFieldValue(FieldInfo.java:280)
at com.google.api.client.util.FieldInfo.setValue(FieldInfo.java:241)
at com.google.api.client.util.GenericData.put(GenericData.java:104)
at com.google.api.client.util.GenericData.put(GenericData.java:48)
at com.google.gson.internal.bind.MapTypeAdapterFactory$Adapter.read(MapTypeAdapterFactory.java:188)
at com.google.gson.internal.bind.MapTypeAdapterFactory$Adapter.read(MapTypeAdapterFactory.java:145)
at com.google.gson.Gson.fromJson(Gson.java:887)
at com.google.gson.Gson.fromJson(Gson.java:852)
at com.google.gson.Gson.fromJson(Gson.java:801)
at com.google.gson.Gson.fromJson(Gson.java:773)
at com.techm.studio.client.JSONTest.main(JSONTest.java:25)
I don't know if I have to register all the nested types upfront and how to do it.
回答1:
It looks like com.google.api.services.*
has it's own com.google.api.client.json.*
package which should be used in this case to serialise model to JSON
and deserialise JSON
to model. See below example:
import com.google.api.client.json.JsonGenerator;
import com.google.api.client.json.JsonParser;
import com.google.api.client.json.jackson2.JacksonFactory;
import com.google.api.services.compute.model.Network;
import com.google.api.services.compute.model.NetworkRoutingConfig;
import java.io.StringWriter;
public class GsonApp {
public static void main(String[] args) throws Exception {
Network network = new Network();
network.setName("k-network");
network.setAutoCreateSubnetworks(false);
network.setDescription("My test network on Google Cloud");
network.setIPv4Range("10.0.0.0/16");
network.setRoutingConfig(new NetworkRoutingConfig().setRoutingMode("REGIONAL"));
JacksonFactory jacksonFactory = new JacksonFactory();
StringWriter writer = new StringWriter();
try (JsonGenerator jsonGenerator = jacksonFactory.createJsonGenerator(writer)) {
jsonGenerator.enablePrettyPrint();
jsonGenerator.serialize(network);
}
String nwkJsonString = writer.toString();
System.out.println("JSON String from POJO ==>\n" + nwkJsonString);
JsonParser jsonParser = jacksonFactory.createJsonParser(nwkJsonString);
Network netwrkOut = jsonParser.parse(Network.class);
System.out.println(netwrkOut.toPrettyString());
}
}
Above code prints:
JSON String from POJO ==>
{
"IPv4Range" : "10.0.0.0/16",
"autoCreateSubnetworks" : false,
"description" : "My test network on Google Cloud",
"name" : "k-network",
"routingConfig" : {
"routingMode" : "REGIONAL"
}
}
{
"IPv4Range" : "10.0.0.0/16",
"autoCreateSubnetworks" : false,
"description" : "My test network on Google Cloud",
"name" : "k-network",
"routingConfig" : {
"routingMode" : "REGIONAL"
}
}
And you do not need to use Gson
.
来源:https://stackoverflow.com/questions/55426453/how-do-i-deserialize-a-json-string-to-java-object-in-app-engine