com.github.hugh.json.gson.GsonUtils Maven / Gradle / Ivy
package com.github.hugh.json.gson;
import com.alibaba.fastjson.JSON;
import com.github.hugh.constant.DateCode;
import com.github.hugh.constant.StrPool;
import com.github.hugh.json.exception.ToolboxJsonException;
import com.github.hugh.json.gson.adapter.CustomDateTypeAdapter;
import com.github.hugh.json.gson.adapter.MapTypeAdapter;
import com.github.hugh.util.DateUtils;
import com.github.hugh.util.EmptyUtils;
import com.github.hugh.util.MapUtils;
import com.github.hugh.util.regex.RegexUtils;
import com.google.common.base.Suppliers;
import com.google.gson.*;
import com.google.gson.internal.LinkedTreeMap;
import com.google.gson.reflect.TypeToken;
import lombok.extern.slf4j.Slf4j;
import java.lang.reflect.Type;
import java.math.BigDecimal;
import java.util.*;
import java.util.function.Supplier;
/**
* gson 工具类
*
* @author hugh
* @since 2.4.10
*/
@Slf4j
public class GsonUtils {
public GsonUtils() {
}
/**
* [年-月-日 时:分:秒]完整的日期格式
*/
protected static final String YEAR_MONTH_DAY_HOUR_MIN_SEC = "yyyy-MM-dd HH:mm:ss";
/**
* 单例模式
*/
private static Supplier gsonSupplier;
/**
* 单例的创建Gson
*
* @return Gson
* @since 1.3.12
*/
public static synchronized Gson getInstance() {
if (gsonSupplier == null) {
Supplier easyRedisSupplier = Gson::new;
gsonSupplier = Suppliers.memoize(easyRedisSupplier::get);
}
return gsonSupplier.get();
}
/**
* 以空值安全的方式从JsonObject中获取一个String.
*
* - 说明:针对{@link com.google.gson.JsonObject}在get其中value时、返回的结果集会默认带上两个""(双引号),需要二次调用{@link JsonElement#getAsString()}方法进行转义成常规没有双引号的结果
* - 但是如果key在JsonObject内没有值时会返回null,导致二次条用需要二次调用其{@link JsonElement#getAsString()}方法出现空指针异常,所以该方法进行二次判断
*
*
* @param jsonObject jsonObject
* @param key KEY
* @return String json中获取key的Integer值,没有返回{@code null}
*/
public static String getString(JsonObject jsonObject, String key) {
JsonElement jsonElement = get(jsonObject, key);
return getAsString(jsonElement);
}
/**
* 方便的方法来获得这个元素的字符串值。
*
* 由于gson 的{@link JsonObject#get(String)}方法返回字符串时前后带有双引号,所以需要再调用{@link JsonElement#getAsString()}
*
*
* 如果元素为{@link JsonArray} 那么直接返回字符串
*
*
* @param jsonElement json元素对象
* @return String
* @since 2.3.0
*/
public static String getAsString(JsonElement jsonElement) {
if (isJsonNull(jsonElement)) {
return null;
}
if (jsonElement.isJsonArray() || jsonElement.isJsonObject()) {
return jsonElement.toString();
}
return jsonElement.getAsString();
}
/**
* 以空值安全的方式从JsonObject中获取一个Integer.
*
* - 说明:针对{@link com.google.gson.JsonObject}在get其中value时、返回的结果集会默认带上两个""(双引号),需要二次调用{@link JsonElement#getAsInt()}方法进行转义成常规没有双引号的结果
* - 但是如果key在JsonObject内没有值时会返回null,导致二次条用需要二次调用其{@link JsonElement#getAsInt()} ()}方法出现空指针异常,所以该方法进行二次判断
*
*
* @param jsonObject jsonObject
* @param key KEY
* @return Integer json中获取key的Integer值,没有返回{@code null}
*/
public static Integer getInteger(JsonObject jsonObject, String key) {
JsonElement jsonElement = get(jsonObject, key);
return isJsonNull(jsonElement) ? null : jsonElement.getAsInt();
}
/**
* 以空值安全的方式从JsonObject中获取一个int.
* 从{@link #getInteger(JsonObject, String)}获取Integer.
*
* @param jsonObject jsonObject
* @param key Key
* @return int json中获取key的Integer值,没有返回{@code 0}
*/
public static int getInt(JsonObject jsonObject, String key) {
Integer integer = getInteger(jsonObject, key);
return integer == null ? 0 : integer;
}
/**
* 以空值安全的方式从JsonObject中获取一个Long.
*
* - 说明:针对{@link com.google.gson.JsonObject}在get其中value时、返回的结果集会默认带上两个""(双引号),需要二次调用{@link JsonElement#getAsLong()}方法进行转义成常规没有双引号的结果
* - 但是如果key在JsonObject内没有值时会返回null,导致二次条用需要二次调用其{@link JsonElement#getAsLong()} ()}方法出现空指针异常,所以该方法进行二次判断
*
*
* @param jsonObject JsonObject
* @param key Key
* @return Long json中没有获取key的value时返回{@code null}
*/
public static Long getLong(JsonObject jsonObject, String key) {
JsonElement jsonElement = get(jsonObject, key);
return isJsonNull(jsonElement) ? null : jsonElement.getAsLong();
}
/**
* 以空值安全的方式从JsonObject中获取一个Long.
* 从{@link #getLong(JsonObject, String)}获取Long.
*
* @param jsonObject JsonObject
* @param key Key
* @return long 在json中获取key的long返回为null时,返回{@code 0}
*/
public static long getLongValue(JsonObject jsonObject, String key) {
Long aLong = getLong(jsonObject, key);
return aLong == null ? 0 : aLong;
}
/**
* 以空值安全的方式从JsonObject中获取一个Long.
*
* - 说明:针对{@link com.google.gson.JsonObject}在get其中value时、返回的结果集会默认带上两个""(双引号),需要二次调用{@link JsonElement#getAsDouble()}方法进行转义成常规没有双引号的结果
* - 但是如果key在JsonObject内没有值时会返回null,导致二次条用需要二次调用其{@link JsonElement#getAsDouble()} ()}方法出现空指针异常,所以该方法进行二次判断
*
*
* @param jsonObject JsonObject
* @param key Key
* @return Double json中获取key的Double值,没有返回{@code null}
*/
public static Double getDouble(JsonObject jsonObject, String key) {
JsonElement jsonElement = get(jsonObject, key);
return isJsonNull(jsonElement) ? null : jsonElement.getAsDouble();
}
/**
* 以空值安全的方式从JsonObject中获取一个Double.
* 从{@link #getDouble(JsonObject, String)}获取Double.
*
* @param jsonObject JsonObject
* @param key Key
* @return double json中获取key的Double值,没有返回{@code 0}
*/
public static double getDoubleValue(JsonObject jsonObject, String key) {
Double aDouble = getDouble(jsonObject, key);
return aDouble == null ? 0 : aDouble;
}
/**
* 以空值安全的方式从JsonObject中获取一个jsonObject
*
* - 说明:针对{@link com.google.gson.JsonObject}在get其中value时、返回的结果集会默认带上两个""(双引号),需要二次调用{@link JsonElement#getAsJsonObject()}方法进行转义成常规没有双引号的结果
* - 但是如果key在JsonObject内没有值时会返回null,导致二次条用需要二次调用其{@link JsonElement#getAsJsonObject()} ()}方法出现空指针异常,所以该方法进行二次判断
*
*
* @param jsonObject JsonObject
* @param key Key
* @return JsonObject json中获取key的JsonObject值,没有返回{@code null}
*/
public static JsonObject getJsonObject(JsonObject jsonObject, String key) {
JsonElement jsonElement = get(jsonObject, key);
return isJsonNull(jsonElement) ? null : jsonElement.getAsJsonObject();
}
/**
* 以空值安全的方式从JsonObject中获取一个JsonArray
*
* - 说明:针对{@link com.google.gson.JsonObject}在get其中value时、返回的结果集会默认带上两个""(双引号),需要二次调用{@link JsonElement#getAsJsonArray()}方法进行转义成常规没有双引号的结果
* - 但是如果key在JsonObject内没有值时会返回null,导致二次条用需要二次调用其{@link JsonElement#getAsJsonArray()} ()}方法出现空指针异常,所以该方法进行二次判断
*
*
* @param jsonObject JsonObject
* @param key Key
* @return JsonArray json中获取key的JsonArray值,没有返回{@code null}
*/
public static JsonArray getJsonArray(JsonObject jsonObject, String key) {
JsonElement jsonElement = get(jsonObject, key);
return isJsonNull(jsonElement) ? null : jsonElement.getAsJsonArray();
}
/**
* 以空值安全的方式从JsonObject中获取一个BigDecimal.
*
* - 说明:针对{@link com.google.gson.JsonObject}在get其中value时、返回的结果集会默认带上两个""(双引号),需要二次调用{@link JsonElement#getAsBigDecimal()}方法进行转义成常规没有双引号的结果
* - 但是如果key在JsonObject内没有值时会返回null,导致二次条用需要二次调用其{@link JsonElement#getAsBigDecimal()} ()}方法出现空指针异常,所以该方法进行二次判断
*
*
* @param jsonObject JsonObject
* @param key Key
* @return JsonArray json中获取key的BigDecimal值,没有返回{@code null}
*/
public static BigDecimal getBigDecimal(JsonObject jsonObject, String key) {
JsonElement jsonElement = get(jsonObject, key);
return isJsonNull(jsonElement) ? null : jsonElement.getAsBigDecimal();
}
/**
* 统一的获取JsonObject中元素方法
*
* @param jsonObject JsonObject
* @param key Key
* @return JsonElement
*/
private static JsonElement get(JsonObject jsonObject, String key) {
if (jsonObject == null) {
throw new ToolboxJsonException("JsonObject is null !");
}
return jsonObject.get(key);
}
/**
* 判断JsonElement是否为null 或者 {@link com.google.gson.JsonNull}
*
* @param jsonElement JsonObject
* @return boolean {@code true} null返回true
* @since 1.3.3
*/
public static boolean isJsonNull(JsonElement jsonElement) {
return jsonElement == null || jsonElement.isJsonNull();
}
/**
* 将Object 解析为 JsonObject
* Object为空时返回{@code null}
*
* @param object 待解析参数
* @param 入参泛型
* @return JsonObject {@link JsonObject}
* @since 1.3.4
*/
public static JsonObject parse(T object) {
return fromJson(object, JsonObject.class);
}
/**
* 将Object 解析为 JsonArray
* Object为空时返回{@code null}
*
* @param object 待解析参数
* @param 入参泛型
* @return JsonArray {@link JsonArray}
* @since 1.3.4
*/
public static JsonArray parseArray(T object) {
JsonElement jsonElement = JsonParser.parseString(String.valueOf(object));
return isJsonNull(jsonElement) ? null : jsonElement.getAsJsonArray();
}
/**
* 将jsonArray 转换为{@link ArrayList}
*
* 由于使用了{@link MapTypeAdapter} 转换器 ,默认返回的结果对象为{@link LinkedTreeMap}
*
*
* @param jsonArray 数组
* @param 泛型
* @return List 集合
* @since 1.3.7
*/
public static List toArrayList(JsonArray jsonArray) {
GsonBuilder gsonBuilder = new GsonBuilder();
Type type = new TypeToken>() {
}.getType();
Gson gson = gsonBuilder
.registerTypeAdapter(type, new MapTypeAdapter()).create();
return gson.fromJson(jsonArray, type);
}
/**
* json数组转 list实体对象
*
* @param jsonArray json数组
* @param clazz 对象
* @param 泛型
* @return List
* @since 2.2.5
*/
public static List toArrayList(JsonArray jsonArray, Class clazz) {
List resultList = new ArrayList<>();
for (JsonElement jsonElement : jsonArray) {
T result;
// if (clazz == null) {
// result = (T) new Jsons(jsonElement);
// } else {
result = JSON.parseObject(jsonElement.toString(), clazz);
// }
resultList.add(result);
}
return resultList;
}
/**
* json数组转 list实体对象
*
* @param str json规则的集合字符串
* @param 泛型
* @return List
* @since 2.3.14
*/
public static List toArrayList(String str) {
return toArrayList(str, null);
}
/**
* json数组转 list实体对象
*
* @param str json规则的集合字符串
* @param clazz 对象
* @param 泛型
* @return List
* @since 2.3.14
*/
public static List toArrayList(String str, Class clazz) {
JsonArray jsonArray = parseArray(str);
if (jsonArray == null) {
throw new ToolboxJsonException("array is null");
}
return toArrayList(jsonArray, clazz);
}
/**
* 对象转换为{@link HashMap}
*
* 使用的自定义的{@link MapTypeAdapter}解析器,重写了数值转换校验
* 该方法转换出来的value数据类型都为{@link String}
* 如需要将实体中的值转换为对应类型的值,使用{@link MapUtils#entityToMap(Object)}
*
* @param object 对象
* @param 对象泛型
* @param 键泛型
* @param value泛型
* @return Map
* @since 1.4.0
*/
public static Map toMap(E object) {
JsonObject jsonObject;
if (object instanceof JsonObject) {
jsonObject = (JsonObject) object;
} else {
jsonObject = parse(object);
}
String strJson = toJson(jsonObject);
Type type = new TypeToken