1. 程式人生 > >json工具類JsonUtils

json工具類JsonUtils

package com.ziyun.pop.common.utils;

import com.alibaba.fastjson.JSONArray;
import com.alibaba.fastjson.JSONObject;
import com.utility.DoubleSerializer;
import com.utility.IntArrayDeserializer;
import com.ziyun.pop.common.e.BaseEnum;
import org.apache.commons.beanutils.BeanUtils;
import org.codehaus.jackson.Version;
import org.codehaus.jackson.map.DeserializationConfig;
import org.codehaus.jackson.map.ObjectMapper;
import org.codehaus.jackson.map.SerializationConfig;
import org.codehaus.jackson.map.annotate.JsonSerialize;
import org.codehaus.jackson.map.module.SimpleModule;
import org.codehaus.jackson.map.type.ArrayType;
import org.codehaus.jackson.map.type.TypeFactory;
import org.codehaus.jackson.type.JavaType;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.slf4j.helpers.FormattingTuple;
import org.slf4j.helpers.MessageFormatter;

import java.beans.BeanInfo;
import java.beans.Introspector;
import java.beans.PropertyDescriptor;
import java.io.StringWriter;
import java.lang.reflect.InvocationTargetException;
import java.lang.reflect.Method;
import java.util.*;

/**
 * json 工具類
 * 
 * @author jiangli
 * @date 2017年11月7日 上午11:28:32
 */
public class JsonUtils {
	private JsonUtils() {
		throw new IllegalAccessError("該類不允許例項化");
	}

	private static final Logger log = LoggerFactory.getLogger(com.utility.JsonUtils.class);

	private static final ObjectMapper mapper;

	private static final ObjectMapper ignoreNullMapper;

	static {
		mapper = new ObjectMapper();
		mapper.enable(DeserializationConfig.Feature.ACCEPT_SINGLE_VALUE_AS_ARRAY);
		SimpleModule module = new SimpleModule("Custom", new Version(1, 0, 0, null));
		module.addDeserializer(int[].class, new IntArrayDeserializer());
		module.addSerializer(Double.class, DoubleSerializer.INSTANCE);
		module.addSerializer(Double.TYPE, DoubleSerializer.INSTANCE);
		mapper.registerModule(module);

		ignoreNullMapper = new ObjectMapper();
		ignoreNullMapper.setSerializationInclusion(JsonSerialize.Inclusion.NON_NULL);
		ignoreNullMapper.configure(SerializationConfig.Feature.WRITE_NULL_MAP_VALUES, false);

		ignoreNullMapper.enable(DeserializationConfig.Feature.ACCEPT_SINGLE_VALUE_AS_ARRAY);
		SimpleModule moduleNull = new SimpleModule("Custom", new Version(1, 0, 0, null));
		moduleNull.addDeserializer(int[].class, new IntArrayDeserializer());
		moduleNull.addSerializer(Double.class, DoubleSerializer.INSTANCE);
		moduleNull.addSerializer(Double.TYPE, DoubleSerializer.INSTANCE);
		ignoreNullMapper.registerModule(moduleNull);

	}

	/**
	 * 將物件轉換為 JSON 的字串格式
	 *
	 * @param object
	 * @return
	 */
	public static String object2String(Object object) {
		return object2String(object, false);
	}

	public static String object2String(Object object, boolean prettyFormat) {
		StringWriter writer = new StringWriter();
		try {
			if (prettyFormat) {
				mapper.writerWithDefaultPrettyPrinter().writeValue(writer, object);
			} else {
				mapper.writeValue(writer, object);
			}
		} catch (Exception e) {
			log.error("將 object 轉換為 json 字串時發生異常:{}", e);
			return null;
		}
		return writer.toString();
	}

	public static String object2StringIgnoreNullField(Object object) {
		return object2StringIgnoreNullField(object, false);
	}

	public static String object2StringIgnoreNullField(Object object, boolean prettyFormat) {
		StringWriter writer = new StringWriter();
		try {
			if (prettyFormat) {
				ignoreNullMapper.writerWithDefaultPrettyPrinter().writeValue(writer, object);
			} else {
				ignoreNullMapper.writeValue(writer, object);
			}
		} catch (Exception e) {
			log.error("將 object 轉換為 json 字串時發生異常:{}", e);
			return null;
		}
		return writer.toString();
	}

	/**
	 * 將 map 轉換為 JSON 的字串格式
	 *
	 * @param map
	 * @return
	 */
	public static String map2String(Map<?, ?> map) {
		StringWriter writer = new StringWriter();
		try {
			mapper.writeValue(writer, map);
		} catch (Exception e) {
			log.error("將 map 轉換為 json 字串時發生異常:{}", e);
			return null;
		}
		return writer.toString();
	}

	/**
	 * 將 JSON 格式的字串轉換為 map
	 *
	 * @param content
	 * @return
	 */
	public static Map<String, Object> string2Map(String content) {
		JavaType type = TypeFactory.defaultInstance().constructMapType(HashMap.class, String.class, Object.class);
		// JavaType type = TypeFactory.mapType(HashMap.class, String.class,
		// Object.class);
		try {
			return mapper.readValue(content, type);
		} catch (Exception e) {
			FormattingTuple message = MessageFormatter.format("將字串[{}]轉換為Map時出現異常", content);
			log.error(message.getMessage(), e);
			throw new RuntimeException(message.getMessage(), e);
		}
	}

	/**
	 * 將 JSON 格式的字串轉換為 map
	 *
	 * @param content
	 * @return
	 */
	public static Map<String, Integer[]> string2MapInts(String content) {
		JavaType type = TypeFactory.defaultInstance().constructMapType(HashMap.class, String.class, Integer[].class);
		// JavaType type = TypeFactory.mapType(HashMap.class, String.class,
		// Object.class);
		try {
			return mapper.readValue(content, type);
		} catch (Exception e) {
			FormattingTuple message = MessageFormatter.format("將字串[{}]轉換為Map時出現異常", content);
			log.error(message.getMessage(), e);
			throw new RuntimeException(message.getMessage(), e);
		}
	}

	/**
	 * 將 JSON 格式的字串轉換為 map
	 *
	 * @param content
	 * @return
	 */
	public static Map<String, String> string2MapString(String content) {
		JavaType type = TypeFactory.defaultInstance().constructMapType(HashMap.class, String.class, String.class);
		// JavaType type = TypeFactory.mapType(HashMap.class, String.class,
		// Object.class);
		try {
			return mapper.readValue(content, type);
		} catch (Exception e) {
			FormattingTuple message = MessageFormatter.format("將字串[{}]轉換為Map時出現異常", content);
			log.error(message.getMessage(), e);
			throw new RuntimeException(message.getMessage(), e);
		}
	}

	/**
	 * 將 JSON 格式的字串轉換為陣列
	 *
	 * @param <T>
	 * @param content
	 *            字串
	 * @param clz
	 *            陣列型別
	 * @return
	 */
	@SuppressWarnings("unchecked")
	public static <T> T[] string2Array(String content, Class<T> clz) {
		JavaType type = ArrayType.construct(TypeFactory.defaultInstance().constructType(clz), null, null);
		try {
			return (T[]) mapper.readValue(content, type);
		} catch (Exception e) {
			FormattingTuple message = MessageFormatter.format("將字串[{}]轉換為陣列時出現異常", content);
			log.error(message.getMessage(), e);
			throw new RuntimeException(message.getMessage(), e);
		}
	}

	/**
	 * 將 JSON 格式的字串轉換為物件
	 *
	 * @param <T>
	 * @param content
	 *            字串
	 * @param clz
	 *            物件型別
	 * @return
	 */
	public static <T> T string2Object(String content, Class<T> clz) {
		JavaType type = TypeFactory.defaultInstance().constructType(clz);
		return string2Object(content, type);
	}

	@SuppressWarnings("unchecked")
	public static <T> T string2Object(String content, JavaType type) {
		try {
			return (T) mapper.readValue(content, type);
		} catch (Exception e) {
			FormattingTuple message = MessageFormatter.format("將字串[{}]轉換為物件[{}]時出現異常",
					new Object[] { content, type, e });
			log.error(message.getMessage(), e);
			throw new RuntimeException(message.getMessage(), e);
		}
	}

	/**
	 * 將 JSON 格式的字串轉換為集合
	 *
	 * @param <T>
	 * @param content
	 *            字串
	 * @param collectionType
	 *            集合型別
	 * @param elementType
	 *            元素型別
	 * @return
	 */
	public static <C extends Collection<E>, E> C string2Collection(String content, Class<C> collectionType,
																   Class<E> elementType) {
		try {
			JavaType type = TypeFactory.defaultInstance().constructCollectionType(collectionType, elementType);
			// JavaType type = TypeFactory.collectionType(collectionType,
			// elementType);
			return mapper.readValue(content, type);
		} catch (Exception e) {
			FormattingTuple message = MessageFormatter.format("將字串[{}]轉換為集合[{}]時出現異常",
					new Object[] { content, collectionType.getSimpleName(), e });
			log.error(message.getMessage(), e);
			throw new RuntimeException(message.getMessage(), e);
		}
	}

	@SuppressWarnings("unchecked")
	public static <K, V> Map<K, V> string2Map(String content, Class<K> keyType, Class<V> valueType) {
		JavaType type = TypeFactory.defaultInstance().constructMapType(HashMap.class, keyType, valueType);
		try {
			return (Map<K, V>) mapper.readValue(content, type);
		} catch (Exception e) {
			FormattingTuple message = MessageFormatter.format("將字串[{}]轉換為Map時出現異常", content);
			log.error(message.getMessage(), e);
			throw new RuntimeException(message.getMessage(), e);
		}
	}

	@SuppressWarnings("unchecked")
	public static <K, V> Map<K, V> string2LinkedHashMap(String content, Class<K> keyType, Class<V> valueType) {
		JavaType type = TypeFactory.defaultInstance().constructMapType(LinkedHashMap.class, keyType, valueType);
		try {
			return (Map<K, V>) mapper.readValue(content, type);
		} catch (Exception e) {
			FormattingTuple message = MessageFormatter.format("將字串[{}]轉換為Map時出現異常", content);
			log.error(message.getMessage(), e);
			throw new RuntimeException(message.getMessage(), e);
		}
	}

	public static Map<?, ?> string2Map(String content, JavaType keyType, JavaType valueType) {
		JavaType type = TypeFactory.defaultInstance().constructMapType(HashMap.class, keyType, valueType);
		try {
			return (Map<?, ?>) mapper.readValue(content, type);
		} catch (Exception e) {
			FormattingTuple message = MessageFormatter.format("將字串[{}]轉換為Map時出現異常", content);
			log.error(message.getMessage(), e);
			throw new RuntimeException(message.getMessage(), e);
		}
	}








	/**
	 * 將一個JSON資料轉換為對應的JAVA物件<br/>
	 * JSON資料中鍵的名稱必須和對應JAVA物件中bean欄位的名稱一致<br/>
	 * 
	 * @param <T>
	 *            java物件值
	 * @param jsonString
	 *            JSON 物件字元
	 * @param cls
	 *            物件class *
	 * @return 返回java物件
	 */
	public static <T> T getJsonToObject(String jsonString, Class<T> cls) {
		return JSONObject.parseObject(jsonString, cls);
	}

	/**
	 * 從json HASH表示式中獲取一個map,改map支援巢狀功能
	 * 
	 * @param jsonString
	 *            json HASH表示式
	 * @return 返回map陣列
	 */
	public static Map<String, Object> jsonToMap(String jsonString) {
		JSONObject jsonObject = JSONObject.parseObject(jsonString);
		Iterator<String> keyIter = jsonObject.keySet().iterator();
		String key;
		Object value;
		Map<String, Object> valueMap = new HashMap<String, Object>();

		while (keyIter.hasNext()) {
			key = (String) keyIter.next();
			value = jsonObject.get(key);
			valueMap.put(key, value);
		}

		return valueMap;
	}

	/**
	 * 從json HASH表示式中獲取一個map,改map支援巢狀功能
	 * @param jsonString json HASH表示式
	 * @return 返回map陣列 Map<String, Object>
	 */
	public static Map<String, String> getMapJsonToStr(String jsonString) {
		JSONObject jsonObject = JSONObject.parseObject(jsonString);
		Iterator<String> keyIter = jsonObject.keySet().iterator();
		String key;
		String value;
		Map<String, String> valueMap = new HashMap<String, String>();

		while (keyIter.hasNext()) {
			key = (String) keyIter.next();
			value = jsonObject.get(key).toString();
			valueMap.put(key, value);
		}

		return valueMap;
	}
	
	/**
	 * 從json HASH表示式中獲取一個map,改map支援巢狀功能
	 * @param jsonString json HASH表示式
	 * @return 返回map陣列  Map<String, Object>
	 */
	public static Map<String, Object> getMapJsonWishStr(String jsonString) {
		JSONObject jsonObject = JSONObject.parseObject(jsonString);
		Iterator<String> keyIter = jsonObject.keySet().iterator();
		String key;
		String value;
		Map<String, Object> valueMap = new HashMap<String, Object>();

		while (keyIter.hasNext()) {
			key = (String) keyIter.next();
			value = jsonObject.get(key).toString();
			valueMap.put(key, value);
		}

		return valueMap;
	}

	/**
	 * 從json物件集合表示式中得到一個java物件集合<br/>
	 * JSON資料中鍵的名稱必須和對應JAVA物件中bean欄位的名稱一致<br/>
	 * @param jsonString json字串
	 * @param cls	JAVA Bean物件
	 * @return JAVA bean物件集合list
	 */
	public static List<?> queryJsonToList(String jsonString, Class<?> cls) {
		List<?> list = JSONArray.parseArray(jsonString, cls);
		return list;
	}
	

	/**
	 * 列舉轉list
	 * 
	 * @param cls
	 *            實現了BaseEnum的子類
	 * @return 轉換失敗返回null
	 */
	@SuppressWarnings("rawtypes")
	public static List<Map<String, Object>> enumToList(Class cls) {
		List<Map<String, Object>> list = null;
		if (cls != null) {
			list = new ArrayList<Map<String, Object>>();
			try {
				Method method = cls.getDeclaredMethod("values");
				BaseEnum[] be = (BaseEnum[]) method.invoke(cls);

				for (BaseEnum e : be) {
					Map<String, Object> map = new HashMap<String, Object>();
					map.put("id", e.toInt());
					map.put("value", e.toCode());
					map.put("describe", e.toDescribe());
					list.add(map);
				}
			} catch (Exception e) {
				return null;
			}
		}
		return list;

	}

	// Bean --> Map 1: 利用Introspector和PropertyDescriptor 將Bean --> Map
	public static Map<String, Object> transBean2Map(Object obj) {

		if(obj == null){
			return null;
		}
		Map<String, Object> map = new HashMap<String, Object>();
		try {
			BeanInfo beanInfo = Introspector.getBeanInfo(obj.getClass());
			PropertyDescriptor[] propertyDescriptors = beanInfo.getPropertyDescriptors();
			for (PropertyDescriptor property : propertyDescriptors) {
				String key = property.getName();
				// 過濾class屬性
				if (!key.equals("class")) {
					// 得到property對應的getter方法
					Method getter = property.getReadMethod();
					Object value = getter.invoke(obj);
					if (value !=null){
						map.put(key, value);
					}
				}

			}
		} catch (Exception e) {
			System.out.println("transBean2Map Error " + e);
		}

		return map;

	}

	/**
	 *
	 *
	 * Map轉換層Bean,使用泛型免去了型別轉換的麻煩。
	 * @param <T>
	 * @param map
	 * @param class1
	 * @return
	 */
	public static <T> T map2Bean(Map<String, String> map, Class<T> class1) {
		T bean = null;
		try {
			bean = class1.newInstance();
			BeanUtils.populate(bean, map);
		} catch (InstantiationException e) {
			e.printStackTrace();
		} catch (IllegalAccessException e) {
			e.printStackTrace();
		} catch (InvocationTargetException e) {
			e.printStackTrace();
		}
		return bean;
	}

	/* 將Map轉換為物件
	* @param paramMap
	* @param cls
	* @return
	*/
	public static <T> T parseMap2Object(Map<String, Object> paramMap, Class<T> cls) {
		return JSONObject.parseObject(JSONObject.toJSONString(paramMap), cls);
	}
}