/* * Copyright (C) 2011 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.internal.bind; import java.io.IOException; import java.net.URI; import java.net.URISyntaxException; import java.net.URL; import java.util.UUID; import com.google.gson.reflect.TypeToken; import com.google.gson.stream.JsonReader; import com.google.gson.stream.JsonWriter; /** * Type adapters for basic types. */ public final class TypeAdapters { private TypeAdapters() {} public static final TypeAdapter BOOLEAN = new TypeAdapter() { public Boolean read(JsonReader reader) throws IOException { return reader.nextBoolean(); } public void write(JsonWriter writer, Boolean value) throws IOException { writer.value(value); } }; public static final TypeAdapter.Factory BOOLEAN_FACTORY = newFactory(boolean.class, Boolean.class, BOOLEAN); public static final TypeAdapter INTEGER = new TypeAdapter() { public Integer read(JsonReader reader) throws IOException { return reader.nextInt(); } public void write(JsonWriter writer, Integer value) throws IOException { writer.value(value); } }; public static final TypeAdapter.Factory INTEGER_FACTORY = newFactory(int.class, Integer.class, INTEGER); public static final TypeAdapter SHORT = new TypeAdapter() { public Short read(JsonReader reader) throws IOException { return (short) reader.nextInt(); } public void write(JsonWriter writer, Short value) throws IOException { writer.value(value); } }; public static final TypeAdapter.Factory SHORT_FACTORY = newFactory(short.class, Short.class, SHORT); public static final TypeAdapter LONG = new TypeAdapter() { public Long read(JsonReader reader) throws IOException { return reader.nextLong(); } public void write(JsonWriter writer, Long value) throws IOException { writer.value(value); } }; public static final TypeAdapter.Factory LONG_FACTORY = newFactory(long.class, Long.class, LONG); public static final TypeAdapter DOUBLE = new TypeAdapter() { public Double read(JsonReader reader) throws IOException { return reader.nextDouble(); } public void write(JsonWriter writer, Double value) throws IOException { writer.value(value); } }; public static final TypeAdapter.Factory DOUBLE_FACTORY = newFactory(double.class, Double.class, DOUBLE); public static final TypeAdapter FLOAT = new TypeAdapter() { public Float read(JsonReader reader) throws IOException { return (float) reader.nextDouble(); } public void write(JsonWriter writer, Float value) throws IOException { writer.value(value); } }; public static final TypeAdapter.Factory FLOAT_FACTORY = newFactory(float.class, Float.class, FLOAT); public static final TypeAdapter STRING = new TypeAdapter() { public String read(JsonReader reader) throws IOException { return reader.nextString(); } public void write(JsonWriter writer, String value) throws IOException { writer.value(value); } }; public static final TypeAdapter.Factory STRING_FACTORY = newFactory(String.class, STRING); public static final TypeAdapter STRING_BUILDER = new TypeAdapter() { public StringBuilder read(JsonReader reader) throws IOException { return new StringBuilder(reader.nextString()); } public void write(JsonWriter writer, StringBuilder value) throws IOException { writer.value(value.toString()); } }; public static final TypeAdapter.Factory STRING_BUILDER_FACTORY = newFactory(StringBuilder.class, STRING_BUILDER); public static final TypeAdapter STRING_BUFFER = new TypeAdapter() { public StringBuffer read(JsonReader reader) throws IOException { return new StringBuffer(reader.nextString()); } public void write(JsonWriter writer, StringBuffer value) throws IOException { writer.value(value.toString()); } }; public static final TypeAdapter.Factory STRING_BUFFER_FACTORY = newFactory(StringBuffer.class, STRING_BUFFER); public static final TypeAdapter URL = new TypeAdapter() { public URL read(JsonReader reader) throws IOException { String nextString = reader.nextString(); return "null".equals(nextString) ? null : new URL(nextString); } public void write(JsonWriter writer, URL value) throws IOException { writer.value(value == null ? null : value.toExternalForm()); } }; public static final TypeAdapter.Factory URL_FACTORY = newFactory(URL.class, URL); public static final TypeAdapter URI = new TypeAdapter() { public URI read(JsonReader reader) throws IOException { try { String nextString = reader.nextString(); return "null".equals(nextString) ? null : new URI(nextString); } catch (URISyntaxException e) { throw new IOException(e); } } public void write(JsonWriter writer, URI value) throws IOException { writer.value(value == null ? null : value.toASCIIString()); } }; public static final TypeAdapter.Factory URI_FACTORY = newFactory(URI.class, URI); public static final TypeAdapter UUID = new TypeAdapter() { public UUID read(JsonReader reader) throws IOException { return java.util.UUID.fromString(reader.nextString()); } public void write(JsonWriter writer, UUID value) throws IOException { writer.value(value.toString()); } }; public static final TypeAdapter.Factory UUID_FACTORY = newFactory(UUID.class, UUID); public static final TypeAdapter EXCLUDED_TYPE_ADAPTER = new TypeAdapter() { @Override public Object read(JsonReader reader) throws IOException { reader.skipValue(); return null; } @Override public void write(JsonWriter writer, Object value) throws IOException { writer.nullValue(); } }; public static TypeAdapter.Factory newFactory( final TypeToken type, final TypeAdapter typeAdapter) { return new TypeAdapter.Factory() { @SuppressWarnings("unchecked") // we use a runtime check to make sure the 'T's equal public TypeAdapter create(MiniGson context, TypeToken typeToken) { return typeToken.equals(type) ? (TypeAdapter) typeAdapter : null; } }; } public static TypeAdapter.Factory newFactory( final Class type, final TypeAdapter typeAdapter) { return new TypeAdapter.Factory() { @SuppressWarnings("unchecked") // we use a runtime check to make sure the 'T's equal public TypeAdapter create(MiniGson context, TypeToken typeToken) { return typeToken.getRawType() == type ? (TypeAdapter) typeAdapter : null; } }; } public static TypeAdapter.Factory newFactory( final Class unboxed, final Class boxed, final TypeAdapter typeAdapter) { return new TypeAdapter.Factory() { @SuppressWarnings("unchecked") // we use a runtime check to make sure the 'T's equal public TypeAdapter create(MiniGson context, TypeToken typeToken) { Class rawType = typeToken.getRawType(); return (rawType == unboxed || rawType == boxed) ? (TypeAdapter) typeAdapter : null; } }; } public static TypeAdapter.Factory newTypeHierarchyFactory( TypeToken type, TypeAdapter typeAdapter) { return new TypeAdapter.Factory() { public TypeAdapter create(MiniGson context, TypeToken typeToken) { // TODO: use Inder's TypeHierarchyAdapter here throw new UnsupportedOperationException(); } }; } }