import java.beans.PropertyDescriptor; import java.lang.reflect.Array; import java.lang.reflect.InvocationTargetException; import java.math.BigDecimal; import java.math.BigInteger; import java.net.URLDecoder; import java.text.ParseException; import java.text.SimpleDateFormat; import java.util.ArrayList; import java.util.Collection; import java.util.HashMap; import java.util.Iterator; import java.util.List; import java.util.Map; import java.util.Set; import java.util.Map.Entry; import ognl.OgnlOps; import org.apache.commons.lang.StringUtils; import org.apache.commons.logging.Log; import org.apache.commons.logging.LogFactory; import org.json.JSONArray; import org.json.JSONObject; import com.opensymphony.xwork.util.OgnlUtil; /** * java对象与json字符串互转的工具类 * */ public class JsonUtil { /** * 将json字符串转成javabean * @param jsonStr 要转换的json字符串 * @param toClass 要转化到的类型 * @param childMap 该类型中集合字段的字段名和集合元素类型map * @return Object * @throws InvocationTargetException * @throws IllegalAccessException * @throws IllegalArgumentException */ @SuppressWarnings("unchecked") public static Object json2Bean(Class toClass,String jsonValue,Map<String,Class> childMap) throws Exception{ if( toClass == null || StringUtils.isBlank(jsonValue)) { return null; } try{ jsonValue = URLDecoder.decode(jsonValue, "utf-8"); }catch(Exception e){ throw new Exception("编码格式错误!"); } JSONObject object = null; try{ object= new JSONObject(jsonValue); }catch(Exception e){ throw new Exception("json格式错误!"); } Object obj = toClass.newInstance(); Map<String,Object> sourceMap = toMap(object); PropertyDescriptor[] props = OgnlUtil.getPropertyDescriptors(obj); Map<String,Object> map = new HashMap<String,Object>(); //参数不区分大小写 for (PropertyDescriptor desc : props) { Set entrys = sourceMap.entrySet(); boolean contains = false; for(Iterator i = entrys.iterator();i.hasNext();){ Entry entry = (Entry) i.next(); if(((String)entry.getKey()).equalsIgnoreCase(desc.getName())){ map.put(desc.getName(), entry.getValue()); contains = true; break; } } if( contains ) { Object value = null; // 处理日期型 // "yyyy-MM-dd'T'HH:mm:ss'Z'"此格式是由json2.js转换后的Date格式 if(java.util.Date.class.isAssignableFrom(desc.getPropertyType())) { String date = (String) map.get(desc.getName()); if(!validateDate(date)){ throw new Exception(desc.getName()+"日期格式错误!"); } value = new SimpleDateFormat("yyyy-MM-dd").parse(date.trim()); } else if(java.sql.Date.class.isAssignableFrom(desc.getPropertyType())) { String date = (String) map.get(desc.getName()); if(!validateDate(date)){ throw new Exception(desc.getName()+"日期格式错误!"); } value = new java.sql.Date(new SimpleDateFormat("yyyy-MM-dd").parse( date.trim()).getTime()); } else if(Collection.class.isAssignableFrom(desc.getPropertyType())) { Class clz = childMap.get(desc.getName()); if(clz.isPrimitive() || CharSequence.class.isAssignableFrom(clz) || Number.class.isAssignableFrom(clz)) value = convertFromStringListSimple(map.get(desc.getName()).toString(),clz); else value = convertFromStringListComplex(map.get(desc.getName()).toString(),clz); } else { if(desc.getPropertyType().isPrimitive() || CharSequence.class.isAssignableFrom(desc.getPropertyType()) || Number.class.isAssignableFrom(desc.getPropertyType())){ try{ value = OgnlOps.convertValue(map.get(desc.getName()), desc.getPropertyType()); }catch(NumberFormatException e){ Class clz = desc.getPropertyType(); if(clz == Integer.TYPE||clz == Short.TYPE||clz == Long.TYPE||clz == BigInteger.class) throw new Exception(desc.getName()+"应为整数!"); else if(clz == Double.TYPE||clz == Float.TYPE||clz == BigDecimal.class) throw new Exception(desc.getName()+"应为数字!"); } } else { value = json2Bean(desc.getPropertyType(),map.get(desc.getName()).toString(),null); } } desc.getWriteMethod().invoke(obj, new Object[] { value }); } } return obj; } /** * 将json字符串转成javabean 日期格式默认为yyyy-MM-dd HH:mm:ss * @param jsonStr 要转换的json字符串 * @param toClass 要转化到的类型 * @param childMap 该类型中集合字段的字段名和集合元素类型map * @param DateStyle 日期时间格式 * @return Object * @throws InvocationTargetException * @throws IllegalAccessException * @throws IllegalArgumentException * @throws ParseException */ @SuppressWarnings("unchecked") public static Object json2Bean(Class toClass,String jsonValue,Map<String,Class> childMap,String DateStyle) throws Exception{ if(StringUtils.isBlank(DateStyle)){ DateStyle = DateUtil.DEFAULT_DATETIME_FORMAT; } if( toClass == null) { return null; } try{ jsonValue = URLDecoder.decode(jsonValue, "utf-8"); }catch(Exception e){ throw new Exception("编码格式错误!"); } JSONObject object = null; try{ object= new JSONObject(jsonValue); }catch(Exception e){ throw new Exception("json格式错误!"); } Object obj = toClass.newInstance(); Map<String,Object> sourceMap = toMap(object); PropertyDescriptor[] props = OgnlUtil.getPropertyDescriptors(obj); Map<String,Object> map = new HashMap<String,Object>(); //参数不区分大小写 for (PropertyDescriptor desc : props) { Set entrys = sourceMap.entrySet(); boolean contains = false; for(Iterator i = entrys.iterator();i.hasNext();){ Entry entry = (Entry) i.next(); if(((String)entry.getKey()).equalsIgnoreCase(desc.getName())){ map.put(desc.getName(), entry.getValue()); contains = true; break; } } if( contains ) { Object value = null; // 处理日期型 // "yyyy-MM-dd'T'HH:mm:ss'Z'"此格式是由json2.js转换后的Date格式 if(java.util.Date.class.isAssignableFrom(desc.getPropertyType())) { String date = (String) map.get(desc.getName()); try{ value = new SimpleDateFormat(DateStyle).parse(date.trim()); }catch(ParseException e3){ throw new Exception(desc.getName()+"="+date+";日期格式错误!"); } } else if(java.sql.Date.class.isAssignableFrom(desc.getPropertyType())) { String date = (String) map.get(desc.getName()); try{ value = new java.sql.Date(new SimpleDateFormat(DateStyle).parse( date.trim()).getTime()); }catch(ParseException e3){ throw new Exception(desc.getName()+"="+date+";日期格式错误!"); } } else if(Collection.class.isAssignableFrom(desc.getPropertyType())) { Class clz = childMap.get(desc.getName()); if(clz.isPrimitive() || CharSequence.class.isAssignableFrom(clz) || Number.class.isAssignableFrom(clz)) value = convertFromStringListSimple(map.get(desc.getName()).toString(),clz); else value = convertFromStringListComplex(map.get(desc.getName()).toString(),clz); } else { if(desc.getPropertyType().isPrimitive() || CharSequence.class.isAssignableFrom(desc.getPropertyType()) || Number.class.isAssignableFrom(desc.getPropertyType())){ try{ value = OgnlOps.convertValue(map.get(desc.getName()), desc.getPropertyType()); }catch(NumberFormatException e){ Class clz = desc.getPropertyType(); if(clz == Integer.TYPE||clz == Short.TYPE||clz == Long.TYPE||clz == BigInteger.class) throw new Exception(desc.getName()+"应为整数!"); else if(clz == Double.TYPE||clz == Float.TYPE||clz == BigDecimal.class) throw new Exception(desc.getName()+"应为数字!"); } } else { value = json2Bean(desc.getPropertyType(),map.get(desc.getName()).toString(),null); } } desc.getWriteMethod().invoke(obj, new Object[] { value }); } } return obj; } public static Map<String,Object> json2Map(String jsonValue) throws Exception{ if (StringUtils.isBlank(jsonValue)) { return null; } try { jsonValue = URLDecoder.decode(jsonValue, "utf-8"); } catch (Exception e) { throw new Exception("编码格式错误!"); } JSONObject object = null; try { object = new JSONObject(jsonValue); } catch (Exception e) { throw new Exception("json格式错误!"); } return toMap(object); } @SuppressWarnings("unchecked") public static List<Map<String,String>> json2List(String jsonValue) throws Exception{ if (StringUtils.isBlank(jsonValue)) { return null; } try { jsonValue = URLDecoder.decode(jsonValue, "utf-8"); } catch (Exception e) { throw new Exception("编码格式错误!"); } JSONArray array = new JSONArray(jsonValue); List<Map<String,String>> jsonList = new ArrayList<Map<String,String>>(); for(int i=0;i<array.length();i++){ Map jsonMap = toMap(array.getJSONObject(i)); jsonList.add(jsonMap); } return jsonList; } public static boolean validateDate(String date) { if(date == null ||date.trim().length() != 10) return false; else { date = date.trim(); String[] param = date.split("-"); if(param[0].length() != 4) return false; int month = Integer.parseInt(param[1]); if(month < 1 || month > 12) return false; int day = Integer.parseInt(param[2]); if(day < 1 || day > 31) return false; } return true; } @SuppressWarnings("unchecked") private static Object convertFromStringListSimple (String jsonValue,Class toClass) throws Exception { if( toClass == null) { return null; } ArrayList<Object> list = new ArrayList<Object>(); JSONArray array = new JSONArray(jsonValue); int i; Object value = null; for(i = 0; i < array.length(); i++) { Object property = array.get(i); if(java.util.Date.class.isAssignableFrom(toClass)) { String date = (String)property; if(!validateDate(date)){ throw new Exception("日期格式错误!"); } value = new SimpleDateFormat("yyyy-MM-dd").parse(date.trim()); } else if(java.sql.Date.class.isAssignableFrom(toClass)){ String date = (String)property; if(!validateDate(date)){ throw new Exception("日期格式错误!"); } value = new java.sql.Date(new SimpleDateFormat("yyyy-MM-dd").parse( date.trim()).getTime()); } else value = OgnlOps.convertValue(property, toClass); list.add(value); } return list; } @SuppressWarnings("unchecked") private static Object convertFromStringListComplex( String jsonValue, Class toClass) throws Exception{ if( toClass == null) { return null; } ArrayList<Object> list = new ArrayList<Object>(); JSONArray array = new JSONArray(jsonValue); for (int i = 0; i < array.length(); i++) { Object obj = toClass.newInstance(); Map map = toMap(array.getJSONObject(i)); PropertyDescriptor[] props = OgnlUtil.getPropertyDescriptors(obj); for (PropertyDescriptor desc : props) { if( map.containsKey(desc.getName()) ) { Object value = null; // 处理日期型 // "yyyy-MM-dd'T'HH:mm:ss'Z'"此格式是由json2.js转换后的Date格式 if(java.util.Date.class.isAssignableFrom(desc.getPropertyType())) { String date = (String) map.get(desc.getName()); if(!validateDate(date)){ throw new Exception(desc.getName()+"日期格式错误!"); } value = new SimpleDateFormat("yyyy-MM-dd").parse(date.trim()); } else if(java.sql.Date.class.isAssignableFrom(desc.getPropertyType())) { String date = (String) map.get(desc.getName()); if(!validateDate(date)){ throw new Exception(desc.getName()+"日期格式错误!"); } value = new java.sql.Date(new SimpleDateFormat("yyyy-MM-dd").parse( date.trim()).getTime()); } else { try{ value = OgnlOps.convertValue(map.get(desc.getName()), desc.getPropertyType()); }catch(NumberFormatException e){ Class clz = desc.getPropertyType(); if(clz == Integer.class||clz == Short.class||clz == Long.class||clz == BigInteger.class) throw new Exception(desc.getName()+"应为整数!"); else if(clz == Double.class||clz == Float.class||clz == BigDecimal.class) throw new Exception(desc.getName()+"应为数字!"); } } desc.getWriteMethod().invoke(obj, new Object[] { value }); } } list.add(obj); } return list; } @SuppressWarnings("unchecked") private static Map<String,Object> toMap(JSONObject object) throws Exception { HashMap<String, Object> map = new HashMap<String, Object>(); Iterator iter = object.keys(); while (iter.hasNext()) { String key = (String) iter.next(); Object val = object.get(key); if(val != null && !val.toString().trim().equals("")) map.put(key,val); } return map; } /** * 将javabean转成json字符串 * @param cls 要转的javabean类型 * @param value 要转的javabean * @return String * */ public static String bean2Json(Class<?> cls, Object value) { try { return transToJSONObject(cls, value).toString(); } catch (Exception e) { log.error("转换jsonObject失败",e); return null; } } // 将value转换成JSONObject @SuppressWarnings("unchecked") private static Object transToJSONObject(Class<?> cls, Object value) throws Exception { Object json = null; if (value != null) { if (Collection.class.isAssignableFrom(cls)) { // 列表s Iterator iter = ((Collection) value).iterator(); JSONArray array = new JSONArray(); while (iter.hasNext()) { Object element = iter.next(); if( element != null ) { array.put(transToJSONObject(element.getClass(), element)); } } json = array; } else if (cls.isArray()) { // 数组 JSONArray array = new JSONArray(); int length = Array.getLength(value); for (int i = 0; i < length; i++) { Object element = Array.get(value, i); if( element != null ) { array.put(transToJSONObject(element.getClass(), element)); } } json = array; } else if (Map.class.isAssignableFrom(cls)) { // 映射 Iterator iter = ((Map) value).entrySet().iterator(); JSONObject object = new JSONObject(); while (iter.hasNext()) { Map.Entry entry = (Map.Entry) iter.next(); Object v = entry.getValue(); if( v != null ) { object.put(entry.getKey().toString(), transToJSONObject(v.getClass(), v)); } } json = object; } else if (cls.isPrimitive() || CharSequence.class.isAssignableFrom(cls) || Number.class.isAssignableFrom(cls)) { // 基本类型、数值或字符串 if (cls == Boolean.TYPE || cls == Integer.TYPE || cls == Float.TYPE || cls == Double.TYPE || cls == Long.TYPE || cls == Short.TYPE || cls == Byte.TYPE || cls.isAssignableFrom(Number.class)) { json = value; } else { json = value.toString(); } } else if (java.util.Date.class.isAssignableFrom(cls) || java.sql.Date.class.isAssignableFrom(cls)) { json = value.toString(); } else { // 对象 Map map = OgnlUtil.getBeanMap(value); JSONObject object = new JSONObject(); if ( map != null ) { Iterator iter = map.entrySet().iterator(); while (iter.hasNext()) { Map.Entry element = (Map.Entry) iter.next(); Object v = element.getValue(); if( v != null ) { object.put((String)element.getKey(), transToJSONObject(v.getClass(), v)); }else{ object.put((String)element.getKey(), "null"); } } json = object; } } } return json == null ? "" : json; } @SuppressWarnings("unchecked") public static void main(String args[]) throws Exception{ String str = "[\"1\",\"2\",\"3\",\"4\"]"; ArrayList list = (ArrayList)JsonUtil.json2Bean(ArrayList.class, str, null); System.out.println(list.get(0)); } private static Log log = LogFactory.getLog(JsonUtil.class); }?