blob: b41e3126956f8aceeed96ebe29b3c67832b097cd [file] [log] [blame]
package brooklyn.event.feed.http;
import java.lang.reflect.Array;
import java.math.BigDecimal;
import java.math.BigInteger;
import com.google.common.base.Function;
import com.google.gson.JsonArray;
import com.google.gson.JsonElement;
import com.google.gson.JsonParser;
public class JsonFunctions {
private JsonFunctions() {} // instead use static utility methods
public static Function<String, JsonElement> asJson() {
return new Function<String, JsonElement>() {
@Override public JsonElement apply(String input) {
return new JsonParser().parse(input);
}
};
}
public static Function<JsonElement, JsonElement> walk(final String... elements) {
return new Function<JsonElement, JsonElement>() {
@Override public JsonElement apply(JsonElement input) {
JsonElement curr = input;
for (String element : elements) {
curr = curr.getAsJsonObject().get(element);
}
return curr;
}
};
}
public static <T> Function<JsonElement, T> cast(final Class<T> expected) {
return new Function<JsonElement, T>() {
@Override public T apply(JsonElement input) {
if (input == null) {
return (T) null;
} else if (input.isJsonNull()) {
return (T) null;
} else if (expected == boolean.class || expected == Boolean.class) {
return (T) (Boolean) input.getAsBoolean();
} else if (expected == char.class || expected == Character.class) {
return (T) (Character) input.getAsCharacter();
} else if (expected == byte.class || expected == Byte.class) {
return (T) (Byte) input.getAsByte();
} else if (expected == short.class || expected == Short.class) {
return (T) (Short) input.getAsShort();
} else if (expected == int.class || expected == Integer.class) {
return (T) (Integer) input.getAsInt();
} else if (expected == long.class || expected == Long.class) {
return (T) (Long) input.getAsLong();
} else if (expected == float.class || expected == Float.class) {
return (T) (Float) input.getAsFloat();
} else if (expected == double.class || expected == Double.class) {
return (T) (Double) input.getAsDouble();
} else if (expected == BigDecimal.class) {
return (T) input.getAsBigDecimal();
} else if (expected == BigInteger.class) {
return (T) input.getAsBigInteger();
} else if (Number.class.isAssignableFrom(expected)) {
// TODO Will result in a class-cast if it's an unexpected sub-type of Number not handled above
return (T) input.getAsNumber();
} else if (expected == String.class) {
return (T) input.getAsString();
} else if (expected.isArray()) {
JsonArray array = input.getAsJsonArray();
Class<?> componentType = expected.getComponentType();
if (JsonElement.class.isAssignableFrom(componentType)) {
JsonElement[] result = new JsonElement[array.size()];
for (int i = 0; i < array.size(); i++) {
result[i] = array.get(i);
}
return (T) result;
} else {
Object[] result = (Object[]) Array.newInstance(componentType, array.size());
for (int i = 0; i < array.size(); i++) {
result[i] = cast(componentType).apply(array.get(i));
}
return (T) result;
}
} else {
throw new IllegalArgumentException("Cannot cast json element to type "+expected);
}
}
};
}
}