/* * Copyright (C) 2008 Google Inc. * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at * * http://www.apache.org/licenses/LICENSE-2.0 * * Unless required by applicable law or agreed to in writing, software * distributed under the License is distributed on an "AS IS" BASIS, * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. * See the License for the specific language governing permissions and * limitations under the License. */ package com.google.gson; import com.google.gson.stream.JsonReader; import com.google.gson.stream.JsonToken; import com.google.gson.stream.JsonWriter; import com.google.gson.stream.MalformedJsonException; import java.io.IOException; import java.io.Reader; import java.io.StringReader; import java.io.StringWriter; import java.io.Writer; import java.lang.reflect.Modifier; import java.lang.reflect.Type; import java.util.LinkedList; import java.util.List; import java.util.Map; /** * This is the main class for using Gson. Gson is typically used by first constructing a * Gson instance and then invoking {@link #toJson(Object)} or {@link #fromJson(String, Class)} * methods on it. * *
You can create a Gson instance by invoking {@code new Gson()} if the default configuration * is all you need. You can also use {@link GsonBuilder} to build a Gson instance with various * configuration options such as versioning support, pretty printing, custom * {@link JsonSerializer}s, {@link JsonDeserializer}s, and {@link InstanceCreator}s.
* *Here is an example of how Gson is used for a simple Class: * *
* Gson gson = new Gson(); // Or use new GsonBuilder().create(); * MyType target = new MyType(); * String json = gson.toJson(target); // serializes target to Json * MyType target2 = gson.fromJson(json, MyType.class); // deserializes json into target2 ** *
If the object that your are serializing/deserializing is a {@code ParameterizedType} * (i.e. contains at least one type parameter and may be an array) then you must use the * {@link #toJson(Object, Type)} or {@link #fromJson(String, Type)} method. Here is an * example for serializing and deserialing a {@code ParameterizedType}: * *
* Type listType = new TypeToken<List<String>>() {}.getType(); * List<String> target = new LinkedList<String>(); * target.add("blah"); * * Gson gson = new Gson(); * String json = gson.toJson(target, listType); * List<String> target2 = gson.fromJson(json, listType); ** *
See the Gson User Guide * for a more complete set of examples.
* * @see com.google.gson.reflect.TypeToken * * @author Inderjeet Singh * @author Joel Leitch */ public final class Gson { //TODO(inder): get rid of all the registerXXX methods and take all such parameters in the // constructor instead. At the minimum, mark those methods private. static final boolean DEFAULT_JSON_NON_EXECUTABLE = false; // Default instances of plug-ins static final AnonymousAndLocalClassExclusionStrategy DEFAULT_ANON_LOCAL_CLASS_EXCLUSION_STRATEGY = new AnonymousAndLocalClassExclusionStrategy(); static final SyntheticFieldExclusionStrategy DEFAULT_SYNTHETIC_FIELD_EXCLUSION_STRATEGY = new SyntheticFieldExclusionStrategy(true); static final ModifierBasedExclusionStrategy DEFAULT_MODIFIER_BASED_EXCLUSION_STRATEGY = new ModifierBasedExclusionStrategy(new int[] { Modifier.TRANSIENT, Modifier.STATIC }); static final FieldNamingStrategy2 DEFAULT_NAMING_POLICY = new SerializedNameAnnotationInterceptingNamingPolicy(new JavaFieldNamingPolicy()); private static final ExclusionStrategy DEFAULT_EXCLUSION_STRATEGY = createExclusionStrategy(); private static final String JSON_NON_EXECUTABLE_PREFIX = ")]}'\n"; private final ExclusionStrategy deserializationExclusionStrategy; private final ExclusionStrategy serializationExclusionStrategy; private final FieldNamingStrategy2 fieldNamingPolicy; private final MappedObjectConstructor objectConstructor; /** Map containing Type or Class objects as keys */ private final ParameterizedTypeHandlerMaptoJson
methods is in compact representation. This
* means that all the unneeded white-space is removed. You can change this behavior with
* {@link GsonBuilder#setPrettyPrinting()}. versionNumber
will be output as "versionNumber@quot;
in
* Json. The same rules are applied for mapping incoming Json to the Java classes. You can
* change this policy through {@link GsonBuilder#setFieldNamingPolicy(FieldNamingPolicy)}.transient
or static
fields from
* consideration for serialization and deserialization. You can change this behavior through
* {@link GsonBuilder#excludeFieldsWithModifiers(int...)}.* Type typeOfSrc = new TypeToken<Collection<Foo>>(){}.getType(); ** @return Json representation of {@code src} * @since 1.4 */ public JsonElement toJsonTree(Object src, Type typeOfSrc) { JsonSerializationContext context = new JsonSerializationContext( new ObjectNavigator(serializationExclusionStrategy), fieldNamingPolicy, serializeNulls, serializers); return context.serialize(src, typeOfSrc); } /** * This method serializes the specified object into its equivalent Json representation. * This method should be used when the specified object is not a generic type. This method uses * {@link Class#getClass()} to get the type for the specified object, but the * {@code getClass()} loses the generic type information because of the Type Erasure feature * of Java. Note that this method works fine if the any of the object fields are of generic type, * just the object itself should not be of a generic type. If the object is of generic type, use * {@link #toJson(Object, Type)} instead. If you want to write out the object to a * {@link Writer}, use {@link #toJson(Object, Appendable)} instead. * * @param src the object for which Json representation is to be created setting for Gson * @return Json representation of {@code src}. */ public String toJson(Object src) { if (src == null) { return toJson(JsonNull.createJsonNull()); } return toJson(src, src.getClass()); } /** * This method serializes the specified object, including those of generic types, into its * equivalent Json representation. This method must be used if the specified object is a generic * type. For non-generic objects, use {@link #toJson(Object)} instead. If you want to write out * the object to a {@link Appendable}, use {@link #toJson(Object, Type, Appendable)} instead. * * @param src the object for which JSON representation is to be created * @param typeOfSrc The specific genericized type of src. You can obtain * this type by using the {@link com.google.gson.reflect.TypeToken} class. For example, * to get the type for {@code Collection
* Type typeOfSrc = new TypeToken<Collection<Foo>>(){}.getType(); ** @return Json representation of {@code src} */ public String toJson(Object src, Type typeOfSrc) { StringWriter writer = new StringWriter(); toJson(toJsonTree(src, typeOfSrc), writer); return writer.toString(); } /** * This method serializes the specified object into its equivalent Json representation. * This method should be used when the specified object is not a generic type. This method uses * {@link Class#getClass()} to get the type for the specified object, but the * {@code getClass()} loses the generic type information because of the Type Erasure feature * of Java. Note that this method works fine if the any of the object fields are of generic type, * just the object itself should not be of a generic type. If the object is of generic type, use * {@link #toJson(Object, Type, Appendable)} instead. * * @param src the object for which Json representation is to be created setting for Gson * @param writer Writer to which the Json representation needs to be written * @throws JsonIOException if there was a problem writing to the writer * @since 1.2 */ public void toJson(Object src, Appendable writer) throws JsonIOException { if (src != null) { toJson(src, src.getClass(), writer); } else { toJson(JsonNull.createJsonNull(), writer); } } /** * This method serializes the specified object, including those of generic types, into its * equivalent Json representation. This method must be used if the specified object is a generic * type. For non-generic objects, use {@link #toJson(Object, Appendable)} instead. * * @param src the object for which JSON representation is to be created * @param typeOfSrc The specific genericized type of src. You can obtain * this type by using the {@link com.google.gson.reflect.TypeToken} class. For example, * to get the type for {@code Collection
* Type typeOfSrc = new TypeToken<Collection<Foo>>(){}.getType(); ** @param writer Writer to which the Json representation of src needs to be written. * @throws JsonIOException if there was a problem writing to the writer * @since 1.2 */ public void toJson(Object src, Type typeOfSrc, Appendable writer) throws JsonIOException { JsonElement jsonElement = toJsonTree(src, typeOfSrc); toJson(jsonElement, writer); } /** * Writes the JSON representation of {@code src} of type {@code typeOfSrc} to * {@code writer}. * @throws JsonIOException if there was a problem writing to the writer */ public void toJson(Object src, Type typeOfSrc, JsonWriter writer) throws JsonIOException { toJson(toJsonTree(src, typeOfSrc), writer); } /** * Converts a tree of {@link JsonElement}s into its equivalent JSON representation. * * @param jsonElement root of a tree of {@link JsonElement}s * @return JSON String representation of the tree * @since 1.4 */ public String toJson(JsonElement jsonElement) { StringWriter writer = new StringWriter(); toJson(jsonElement, writer); return writer.toString(); } /** * Writes out the equivalent JSON for a tree of {@link JsonElement}s. * * @param jsonElement root of a tree of {@link JsonElement}s * @param writer Writer to which the Json representation needs to be written * @throws JsonIOException if there was a problem writing to the writer * @since 1.4 */ public void toJson(JsonElement jsonElement, Appendable writer) throws JsonIOException { try { if (generateNonExecutableJson) { writer.append(JSON_NON_EXECUTABLE_PREFIX); } JsonWriter jsonWriter = new JsonWriter(Streams.writerForAppendable(writer)); if (prettyPrinting) { jsonWriter.setIndent(" "); } toJson(jsonElement, jsonWriter); } catch (IOException e) { throw new RuntimeException(e); } } /** * Writes the JSON for {@code jsonElement} to {@code writer}. * @throws JsonIOException if there was a problem writing to the writer */ public void toJson(JsonElement jsonElement, JsonWriter writer) throws JsonIOException { boolean oldLenient = writer.isLenient(); writer.setLenient(true); boolean oldHtmlSafe = writer.isHtmlSafe(); writer.setHtmlSafe(htmlSafe); try { Streams.write(jsonElement, serializeNulls, writer); } catch (IOException e) { throw new JsonIOException(e); } finally { writer.setLenient(oldLenient); writer.setHtmlSafe(oldHtmlSafe); } } /** * This method deserializes the specified Json into an object of the specified class. It is not * suitable to use if the specified class is a generic type since it will not have the generic * type information because of the Type Erasure feature of Java. Therefore, this method should not * be used if the desired type is a generic type. Note that this method works fine if the any of * the fields of the specified object are generics, just the object itself should not be a * generic type. For the cases when the object is of generic type, invoke * {@link #fromJson(String, Type)}. If you have the Json in a {@link Reader} instead of * a String, use {@link #fromJson(Reader, Class)} instead. * * @param
* Type typeOfT = new TypeToken<Collection<Foo>>(){}.getType(); ** @return an object of type T from the string * @throws JsonParseException if json is not a valid representation for an object of type typeOfT * @throws JsonSyntaxException if json is not a valid representation for an object of type */ @SuppressWarnings("unchecked") public
* Type typeOfT = new TypeToken<Collection<Foo>>(){}.getType(); ** @return an object of type T from the json * @throws JsonIOException if there was a problem reading from the Reader * @throws JsonSyntaxException if json is not a valid representation for an object of type * @since 1.2 */ public
* Type typeOfT = new TypeToken<Collection<Foo>>(){}.getType(); ** @return an object of type T from the json * @throws JsonSyntaxException if json is not a valid representation for an object of type typeOfT * @since 1.3 */ @SuppressWarnings("unchecked") public