diff --git a/gson/src/main/java/com/google/gson/TypeAdapter.java b/gson/src/main/java/com/google/gson/TypeAdapter.java
index d02a3bc3..6477b55d 100644
--- a/gson/src/main/java/com/google/gson/TypeAdapter.java
+++ b/gson/src/main/java/com/google/gson/TypeAdapter.java
@@ -16,18 +16,17 @@
package com.google.gson;
-import java.io.IOException;
-import java.io.Reader;
-import java.io.StringReader;
-import java.io.StringWriter;
-import java.io.Writer;
-
import com.google.gson.internal.bind.JsonElementWriter;
import com.google.gson.internal.bind.JsonTreeReader;
import com.google.gson.reflect.TypeToken;
import com.google.gson.stream.JsonReader;
import com.google.gson.stream.JsonToken;
import com.google.gson.stream.JsonWriter;
+import java.io.IOException;
+import java.io.Reader;
+import java.io.StringReader;
+import java.io.StringWriter;
+import java.io.Writer;
/**
* Converts Java objects to and from JSON.
@@ -94,28 +93,30 @@ import com.google.gson.stream.JsonWriter;
* Gson gson = builder.create();
* }
*
- *
JSON Conversion
- * A type adapter registered with Gson is automatically invoked while serializing
- * or deserializing JSON. However, you can also use type adapters directly to serialize
- * and deserialize JSON. Here is an example for deserialization:
{@code
- *
- * String json = "{'origin':'0,0','points':['1,2','3,4']}";
- * TypeAdapter graphAdapter = gson.getAdapter(Graph.class);
- * Graph graph = graphAdapter.fromJson(json);
- * }
- * And an example for serialization: {@code
- *
- * Graph graph = new Graph(...);
- * TypeAdapter graphAdapter = gson.getAdapter(Graph.class);
- * String json = graphAdapter.toJson(graph);
- * }
- *
- * Type adapters are type-specific. For example, a {@code
- * TypeAdapter} can convert {@code Date} instances to JSON and JSON to
- * instances of {@code Date}, but cannot convert any other types.
- *
* @since 2.1
*/
+// non-Javadoc:
+//
+// JSON Conversion
+// A type adapter registered with Gson is automatically invoked while serializing
+// or deserializing JSON. However, you can also use type adapters directly to serialize
+// and deserialize JSON. Here is an example for deserialization:
{@code
+//
+// String json = "{'origin':'0,0','points':['1,2','3,4']}";
+// TypeAdapter graphAdapter = gson.getAdapter(Graph.class);
+// Graph graph = graphAdapter.fromJson(json);
+// }
+// And an example for serialization: {@code
+//
+// Graph graph = new Graph(...);
+// TypeAdapter graphAdapter = gson.getAdapter(Graph.class);
+// String json = graphAdapter.toJson(graph);
+// }
+//
+// Type adapters are type-specific. For example, a {@code
+// TypeAdapter} can convert {@code Date} instances to JSON and JSON to
+// instances of {@code Date}, but cannot convert any other types.
+//
public abstract class TypeAdapter {
/**
@@ -136,7 +137,7 @@ public abstract class TypeAdapter {
*
* @param value the Java object to convert. May be null.
*/
- public final void toJson(Writer out, T value) throws IOException {
+ /*public*/ final void toJson(Writer out, T value) throws IOException {
JsonWriter writer = new JsonWriter(out);
write(writer, value);
}
@@ -181,7 +182,7 @@ public abstract class TypeAdapter {
* }
* Note that we didn't need to check for nulls in our type adapter after we used nullSafe.
*/
- public TypeAdapter nullSafe() {
+ public final TypeAdapter nullSafe() {
return new TypeAdapter() {
@Override public void write(JsonWriter out, T value) throws IOException {
if (value == null) {
@@ -209,7 +210,7 @@ public abstract class TypeAdapter {
*
* @param value the Java object to convert. May be null.
*/
- public final String toJson(T value) throws IOException {
+ /*public*/ final String toJson(T value) throws IOException {
StringWriter stringWriter = new StringWriter();
toJson(stringWriter, value);
return stringWriter.toString();
@@ -221,7 +222,7 @@ public abstract class TypeAdapter {
* @param value the Java object to convert. May be null.
* @return the converted JSON tree. May be {@link JsonNull}.
*/
- public JsonElement toJsonTree(T value) {
+ /*public*/ final JsonElement toJsonTree(T value) {
try {
JsonElementWriter jsonWriter = new JsonElementWriter();
jsonWriter.setLenient(true);
@@ -248,7 +249,7 @@ public abstract class TypeAdapter {
*
* @return the converted Java object. May be null.
*/
- public final T fromJson(Reader in) throws IOException {
+ /*public*/ final T fromJson(Reader in) throws IOException {
JsonReader reader = new JsonReader(in);
reader.setLenient(true); // TODO: non-lenient?
return read(reader);
@@ -262,7 +263,7 @@ public abstract class TypeAdapter {
*
* @return the converted Java object. May be null.
*/
- public final T fromJson(String json) throws IOException {
+ /*public*/ final T fromJson(String json) throws IOException {
return fromJson(new StringReader(json));
}
@@ -271,7 +272,7 @@ public abstract class TypeAdapter {
*
* @param jsonTree the Java object to convert. May be {@link JsonNull}.
*/
- public T fromJsonTree(JsonElement jsonTree) {
+ /*public*/ final T fromJsonTree(JsonElement jsonTree) {
try {
JsonReader jsonReader = new JsonTreeReader(jsonTree);
jsonReader.setLenient(true);
diff --git a/gson/src/main/java/com/google/gson/internal/bind/MapTypeAdapterFactory.java b/gson/src/main/java/com/google/gson/internal/bind/MapTypeAdapterFactory.java
index 12b1fdf3..7e395089 100644
--- a/gson/src/main/java/com/google/gson/internal/bind/MapTypeAdapterFactory.java
+++ b/gson/src/main/java/com/google/gson/internal/bind/MapTypeAdapterFactory.java
@@ -18,6 +18,7 @@ package com.google.gson.internal.bind;
import com.google.gson.Gson;
import com.google.gson.JsonElement;
+import com.google.gson.JsonIOException;
import com.google.gson.JsonPrimitive;
import com.google.gson.JsonSyntaxException;
import com.google.gson.TypeAdapter;
@@ -215,7 +216,7 @@ public final class MapTypeAdapterFactory implements TypeAdapter.Factory {
List values = new ArrayList(map.size());
for (Map.Entry entry : map.entrySet()) {
- JsonElement keyElement = keyTypeAdapter.toJsonTree(entry.getKey());
+ JsonElement keyElement = toJsonTree(keyTypeAdapter, entry.getKey());
keys.add(keyElement);
values.add(entry.getValue());
hasComplexKeys |= keyElement.isJsonArray() || keyElement.isJsonObject();
@@ -260,4 +261,16 @@ public final class MapTypeAdapterFactory implements TypeAdapter.Factory {
}
}
}
+
+ // TODO: remove this when TypeAdapter.toJsonTree() is public
+ private static JsonElement toJsonTree(TypeAdapter typeAdapter, T value) {
+ try {
+ JsonElementWriter jsonWriter = new JsonElementWriter();
+ jsonWriter.setLenient(true);
+ typeAdapter.write(jsonWriter, value);
+ return jsonWriter.get();
+ } catch (IOException e) {
+ throw new JsonIOException(e);
+ }
+ }
}
diff --git a/gson/src/test/java/com/google/gson/functional/StreamingTypeAdaptersTest.java b/gson/src/test/java/com/google/gson/functional/StreamingTypeAdaptersTest.java
index 8002d216..e01e1077 100644
--- a/gson/src/test/java/com/google/gson/functional/StreamingTypeAdaptersTest.java
+++ b/gson/src/test/java/com/google/gson/functional/StreamingTypeAdaptersTest.java
@@ -16,16 +16,6 @@
package com.google.gson.functional;
-import java.io.IOException;
-import java.util.ArrayList;
-import java.util.Arrays;
-import java.util.Collections;
-import java.util.LinkedHashMap;
-import java.util.List;
-import java.util.Map;
-
-import junit.framework.TestCase;
-
import com.google.gson.Gson;
import com.google.gson.GsonBuilder;
import com.google.gson.JsonSyntaxException;
@@ -33,6 +23,16 @@ import com.google.gson.TypeAdapter;
import com.google.gson.reflect.TypeToken;
import com.google.gson.stream.JsonReader;
import com.google.gson.stream.JsonWriter;
+import java.io.IOException;
+import java.io.StringReader;
+import java.io.StringWriter;
+import java.util.ArrayList;
+import java.util.Arrays;
+import java.util.Collections;
+import java.util.LinkedHashMap;
+import java.util.List;
+import java.util.Map;
+import junit.framework.TestCase;
public final class StreamingTypeAdaptersTest extends TestCase {
private Gson miniGson = new GsonBuilder().create();
@@ -47,13 +47,13 @@ public final class StreamingTypeAdaptersTest extends TestCase {
assertEquals("{'horsePower':300.0,"
+ "'passengers':[{'age':29,'name':'Jesse'},{'age':29,'name':'Jodie'}]}",
- truckAdapter.toJson(truck).replace('\"', '\''));
+ toJson(truckAdapter, truck).replace('\"', '\''));
}
public void testDeserialize() throws IOException {
String json = "{'horsePower':300.0,"
+ "'passengers':[{'age':29,'name':'Jesse'},{'age':29,'name':'Jodie'}]}";
- Truck truck = truckAdapter.fromJson(json);
+ Truck truck = fromJson(truckAdapter, json);
assertEquals(300.0, truck.horsePower);
assertEquals(Arrays.asList(new Person("Jesse", 29), new Person("Jodie", 29)), truck.passengers);
}
@@ -62,11 +62,11 @@ public final class StreamingTypeAdaptersTest extends TestCase {
Truck truck = new Truck();
truck.passengers = null;
assertEquals("{'horsePower':0.0,'passengers':null}",
- truckAdapter.toJson(truck).replace('\"', '\''));
+ toJson(truckAdapter, truck).replace('\"', '\''));
}
public void testDeserializeNullField() throws IOException {
- Truck truck = truckAdapter.fromJson("{'horsePower':0.0,'passengers':null}");
+ Truck truck = fromJson(truckAdapter, "{'horsePower':0.0,'passengers':null}");
assertNull(truck.passengers);
}
@@ -74,11 +74,11 @@ public final class StreamingTypeAdaptersTest extends TestCase {
Truck truck = new Truck();
truck.passengers = Arrays.asList((Person) null);
assertEquals("{'horsePower':0.0,'passengers':[null]}",
- truckAdapter.toJson(truck).replace('\"', '\''));
+ toJson(truckAdapter, truck).replace('\"', '\''));
}
public void testDeserializeNullObject() throws IOException {
- Truck truck = truckAdapter.fromJson("{'horsePower':0.0,'passengers':[null]}");
+ Truck truck = fromJson(truckAdapter, "{'horsePower':0.0,'passengers':[null]}");
assertEquals(Arrays.asList((Person) null), truck.passengers);
}
@@ -87,12 +87,12 @@ public final class StreamingTypeAdaptersTest extends TestCase {
Truck truck = new Truck();
truck.passengers = Arrays.asList(new Person("Jesse", 29), new Person("Jodie", 29));
assertEquals("{'horsePower':0.0,'passengers':['Jesse','Jodie']}",
- truckAdapter.toJson(truck).replace('\"', '\''));
+ toJson(truckAdapter, truck).replace('\"', '\''));
}
public void testDeserializeWithCustomTypeAdapter() throws IOException {
usePersonNameAdapter();
- Truck truck = truckAdapter.fromJson("{'horsePower':0.0,'passengers':['Jesse','Jodie']}");
+ Truck truck = fromJson(truckAdapter, "{'horsePower':0.0,'passengers':['Jesse','Jodie']}");
assertEquals(Arrays.asList(new Person("Jesse", -1), new Person("Jodie", -1)), truck.passengers);
}
@@ -114,36 +114,36 @@ public final class StreamingTypeAdaptersTest extends TestCase {
Map map = new LinkedHashMap();
map.put("a", 5.0);
map.put("b", 10.0);
- assertEquals("{'a':5.0,'b':10.0}", mapAdapter.toJson(map).replace('"', '\''));
+ assertEquals("{'a':5.0,'b':10.0}", toJson(mapAdapter, map).replace('"', '\''));
}
public void testDeserializeMap() throws IOException {
Map map = new LinkedHashMap();
map.put("a", 5.0);
map.put("b", 10.0);
- assertEquals(map, mapAdapter.fromJson("{'a':5.0,'b':10.0}"));
+ assertEquals(map, fromJson(mapAdapter, "{'a':5.0,'b':10.0}"));
}
public void testSerialize1dArray() throws IOException {
TypeAdapter arrayAdapter = miniGson.getAdapter(new TypeToken() {});
- assertEquals("[1.0,2.0,3.0]", arrayAdapter.toJson(new double[]{1.0, 2.0, 3.0}));
+ assertEquals("[1.0,2.0,3.0]", toJson(arrayAdapter, new double[]{1.0, 2.0, 3.0}));
}
public void testDeserialize1dArray() throws IOException {
TypeAdapter arrayAdapter = miniGson.getAdapter(new TypeToken() {});
- double[] array = arrayAdapter.fromJson("[1.0,2.0,3.0]");
+ double[] array = fromJson(arrayAdapter, "[1.0,2.0,3.0]");
assertTrue(Arrays.toString(array), Arrays.equals(new double[]{1.0, 2.0, 3.0}, array));
}
public void testSerialize2dArray() throws IOException {
TypeAdapter arrayAdapter = miniGson.getAdapter(new TypeToken() {});
double[][] array = { {1.0, 2.0 }, { 3.0 } };
- assertEquals("[[1.0,2.0],[3.0]]", arrayAdapter.toJson(array));
+ assertEquals("[[1.0,2.0],[3.0]]", toJson(arrayAdapter, array));
}
public void testDeserialize2dArray() throws IOException {
TypeAdapter arrayAdapter = miniGson.getAdapter(new TypeToken() {});
- double[][] array = arrayAdapter.fromJson("[[1.0,2.0],[3.0]]");
+ double[][] array = fromJson(arrayAdapter, "[[1.0,2.0],[3.0]]");
double[][] expected = { {1.0, 2.0 }, { 3.0 } };
assertTrue(Arrays.toString(array), Arrays.deepEquals(expected, array));
}
@@ -191,7 +191,7 @@ public final class StreamingTypeAdaptersTest extends TestCase {
assertEquals("{'label':'root',"
+ "'left':{'label':'left','left':null,'right':null},"
+ "'right':{'label':'right','left':null,'right':null}}",
- nodeAdapter.toJson(root).replace('"', '\''));
+ toJson(nodeAdapter, root).replace('"', '\''));
}
static class Truck {
@@ -207,8 +207,6 @@ public final class StreamingTypeAdaptersTest extends TestCase {
this.age = age;
}
- public Person() {} // TODO: use Joel's constructor code so we don't need this
-
@Override public boolean equals(Object o) {
return o instanceof Person
&& ((Person) o).name.equals(name)
@@ -226,6 +224,20 @@ public final class StreamingTypeAdaptersTest extends TestCase {
Node(String label) {
this.label = label;
}
- public Node() {} // TODO: use Joel's constructor code so we don't need this
+ }
+
+ // TODO: remove this when TypeAdapter.toJson() is public
+ private static String toJson(TypeAdapter typeAdapter, T value) throws IOException {
+ StringWriter stringWriter = new StringWriter();
+ JsonWriter writer = new JsonWriter(stringWriter);
+ typeAdapter.write(writer, value);
+ return stringWriter.toString();
+ }
+
+ // TODO: remove this when TypeAdapter.fromJson() is public
+ private T fromJson(TypeAdapter typeAdapter, String json) throws IOException {
+ JsonReader reader = new JsonReader(new StringReader(json));
+ reader.setLenient(true); // TODO: non-lenient?
+ return typeAdapter.read(reader);
}
}