package com.aherp.framework.util;

import java.lang.reflect.Array;
import java.lang.reflect.Method;
import java.util.Collection;
import java.util.Iterator;
import java.util.Map;

import org.json.JSONArray;
import org.json.JSONException;
import org.json.JSONObject;
import org.json.JSONString;

/** *//**
 * JSON工具类,反射的方式转换整个对象
 * @author Jim Wu
 *
 */
public class JSONUtil ...{

private static JSONUtil instance = null;
    
    public JSONUtil()...{}
    
    /** *//**
     * 代理类时做的检查.返回应该检查的对象.
     * @param bean
     * @return
     */
    protected Object proxyCheck(Object bean)...{
        return bean;
    }

static public String toJSONString(Object obj) throws JSONException...{
        return toJSONString(obj, false);
    }
    
    static public String toJSONString(Object obj, boolean useClassConvert) throws JSONException...{
        if(instance == null)
            instance = new JSONUtil();
        return instance.getJSONObject(obj, useClassConvert).toString();
    }

private String getJSONArray(Object arrayObj, boolean useClassConvert) throws JSONException...{
        
        if(arrayObj == null)
            return "null";
        
        arrayObj = proxyCheck(arrayObj);
        
        JSONArray jSONArray = new JSONArray();
        if(arrayObj instanceof Collection)...{
            Iterator iterator = ((Collection)arrayObj).iterator();
            while(iterator.hasNext())...{
                Object rowObj = iterator.next();
                if(rowObj == null)
                    jSONArray.put(new JSONStringObject(null));
                else if(rowObj.getClass().isArray() || rowObj instanceof Collection)
                    jSONArray.put(getJSONArray(rowObj, useClassConvert));
                else
                    jSONArray.put(getJSONObject(rowObj, useClassConvert));
            }
        }
        if(arrayObj.getClass().isArray())...{
            int arrayLength = Array.getLength(arrayObj);
            for(int i = 0; i < arrayLength; i ++)...{
                Object rowObj = Array.get(arrayObj, i);
                if(rowObj == null)
                    jSONArray.put(new JSONStringObject(null));
                else if(rowObj.getClass().isArray() || rowObj instanceof Collection)
                    jSONArray.put(getJSONArray(rowObj, useClassConvert));
                else
                    jSONArray.put(getJSONObject(rowObj, useClassConvert));
            }
        }
        return jSONArray.toString();
    }

JSONStringObject getJSONObject(Object value, boolean useClassConvert) throws JSONException...{

//处理原始类型

if (value == null) ...{
            return new JSONStringObject("null");
        }
        value = proxyCheck(value);
        if (value instanceof JSONString) ...{
            Object o;
            try ...{
                o = ((JSONString)value).toJSONString();
            } catch (Exception e) ...{
                throw new JSONException(e);
            }
            throw new JSONException("Bad value from toJSONString: " + o);
        }
        if (value instanceof Number) ...{
            return new JSONStringObject(JSONObject.numberToString((Number) value));
        }
        if (value instanceof Boolean || value instanceof JSONObject ||
                value instanceof JSONArray) ...{
            return new JSONStringObject(value.toString());
        }
        if (value instanceof String)
            return new JSONStringObject(JSONObject.quote(value.toString()));
        if (value instanceof Map) ...{
            
            JSONObject jSONObject = new JSONObject();

Iterator iterator = ((Map)value).keySet().iterator();
            while(iterator.hasNext())...{
                String key = iterator.next().toString();
                Object valueObj = ((Map)value).get(key);
                jSONObject.put(key, getJSONObject(valueObj, useClassConvert));
            }
            return new JSONStringObject(jSONObject.toString());
        }

//class

if(value instanceof Class)
            return new JSONStringObject(JSONObject.quote(((Class)value).getSimpleName()));
        
        //数组

if (value instanceof Collection || value.getClass().isArray()) ...{
            return new JSONStringObject(getJSONArray(proxyCheck(value), useClassConvert));
        }

return reflectObject(value, useClassConvert);
    }//value.equals(null)

private JSONStringObject reflectObject(Object bean, boolean useClassConvert)...{
        JSONObject jSONObject = new JSONObject();

Class klass = bean.getClass();
        Method[] methods = klass.getMethods();
        for (int i = 0; i < methods.length; i += 1) ...{
            try ...{
                Method method = methods[i];
                String name = method.getName();
                String key = "";
                if (name.startsWith("get")) ...{
                    key = name.substring(3);
                } else if (name.startsWith("is")) ...{
                    key = name.substring(2);
                }
                if (key.length() > 0 &&
                        Character.isUpperCase(key.charAt(0)) &&
                        method.getParameterTypes().length == 0) ...{
                    if (key.length() == 1) ...{
                        key = key.toLowerCase();
                    } else if (!Character.isUpperCase(key.charAt(1))) ...{
                        key = key.substring(0, 1).toLowerCase() +
                            key.substring(1);
                    }
                    Object elementObj = method.invoke(bean, null);
                    if(!useClassConvert && elementObj instanceof Class)
                        continue;

jSONObject.put(key, getJSONObject(elementObj, useClassConvert));
                }
            } catch (Exception e) ...{
                /**//* forget about it */
            }
        }
        return new JSONStringObject(jSONObject.toString());
    }
}

package com.aherp.framework.util;

import org.json.JSONString;

public class JSONStringObject implements JSONString ...{

private String jsonString = null;
    
    public JSONStringObject(String jsonString)...{
        this.jsonString = jsonString;
    }

@Override
    public String toString() ...{
        return jsonString;
    }

public String toJSONString() ...{
        return jsonString;
    }
}

调用测试程序

import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;

public class AObj ...{
    private int ii = 7;
    private boolean bb = true;
    private String ss = "你好";
    private List aList = new ArrayList();

public AObj()...{
        aList.add("hello");
        aList.add(false);
        aList.add(new BObj());
        aList.add(new HashMap());
    }
    
    public boolean isBb() ...{
        return bb;
    }
    public void setBb(boolean bb) ...{
        this.bb = bb;
    }
    public int getIi() ...{
        return ii;
    }
    public void setIi(int ii) ...{
        this.ii = ii;
    }
    public String getSs() ...{
        return ss;
    }
    public void setSs(String ss) ...{
        this.ss = ss;
    }
    public List getAList() ...{
        return aList;
    }
    public void setAList(List list) ...{
        aList = list;
    }
}

import java.math.BigDecimal;
import java.util.HashMap;

public class BObj ...{

private HashMap innerhm = new HashMap();
    
    public BObj()...{
        double dd = 7.4354;
        innerhm.put("gigi", "高兴");
        innerhm.put("sina", new BigDecimal(dd));
    }

public HashMap getInnerhm() ...{
        return innerhm;
    }

public void setInnerhm(HashMap innerhm) ...{
        this.innerhm = innerhm;
    }
}

public class CObj extends AObj...{

private Object[] oarray = new Object[]...{352, false, "kick"};

public Object[] getOarray() ...{
        return oarray;
    }

public void setOarray(Object[] oarray) ...{
        this.oarray = oarray;
    }
}

import java.util.*;

import org.json.JSONException;
import org.json.JSONObject;

import com.aherp.framework.util.HiJSONUtil;
import com.aherp.framework.util.JSONUtil;

public class Test ...{ 
    public static void main(String[] args) throws JSONException ...{
        CObj cObj = new CObj();
        System.out.println("var jsonStr = " + JSONObject.quote(JSONUtil.toJSONString(cObj))+";");
    } 
}

输出:
var jsonStr = "{\"AList\":[\"hello\",false,{\"innerhm\":{\"gigi\":\"高兴\",\"sina\":7.4353999999999995651478457148186862468719482421875}},{}],\"ii\":7,\"oarray\":[352,false,\"kick\"],\"ss\":\"你好\",\"bb\":true}";

如果需要支持Hibernate,那么必须弄清其机制。Hibernate采用CGLIB对VO对象进行字节码增加,实际机制就是使用一个原类型的proxy子类,其子类实现了HibernateProxy接口。其接口有一个isUninitialized的判断方法,用来判断该代理类是否已经初始化(还记得在事务外使用延迟加载的对象会抛no Session的错误吗,正是由于实际使用的对象已经变成原来类的子类proxy了)。而对于one-to-many映射时,很难判断对象只加载一次,因此为了避免递归调用死循环,忽略了Hibernate的one-to-many集合的递归反射。其原理和many-to-one一样,也是一个子类化的proxy,具有PersistentSet的接口。

因此,支持Hibernate的JSONUtil如下:

package com.aherp.framework.util;

import org.hibernate.collection.PersistentSet;
import org.hibernate.proxy.HibernateProxy;
import org.hibernate.proxy.LazyInitializer;
import org.json.JSONException;

/**//**
 * 支持Hibernate的JSONUtil.
 * 自动检测是否已经代理加载,如果未加载,则将对象仅加载为OID
 * @author Jim Wu
 *
 */
public class HiJSONUtil extends JSONUtil ...{

private static HiJSONUtil instance = null;

static public String toJSONString(Object obj) throws JSONException...{
        return toJSONString(obj, false);
    }
    
    static public String toJSONString(Object obj, boolean useClassConvert) throws JSONException...{
        if(instance == null)
            instance = new HiJSONUtil();
        return instance.getJSONObject(obj, useClassConvert).toString();
    }

@Override
    protected Object proxyCheck(Object bean) ...{
        System.out.println("Class is ..." + bean.getClass().getName());
        if(bean instanceof HibernateProxy)...{
            LazyInitializer lazyInitializer = ((HibernateProxy)bean).getHibernateLazyInitializer();
            if(lazyInitializer.isUninitialized())...{
                System.out.println(">>>>>lazyInitializer.getIdentifier()="+ lazyInitializer.getIdentifier());
                return lazyInitializer.getIdentifier();
            }
        }
        if(bean instanceof PersistentSet)...{
            return new String[]...{}; //忽略hibernate one-to-many

}
        return bean;
    }
}
;

 

Json工具类,实现了反射将整个Object转换为Json对象的功能,支持Hibernate的延迟加的更多相关文章

  1. JSON工具类的构建(后端版本)

    前言 在前后端交互的选择上,之前一直采用的是模板引擎(因为我只负责后端). 而这次的一个算是作业吧,前后端都是我,所以就研究了一下JSON交互在java web的应用(主要是前端). 优缺点 前后端耦 ...

  2. 用jackson封装的JSON工具类

    package hjp.smart4j.framework.util; import com.fasterxml.jackson.databind.ObjectMapper; import org.s ...

  3. Code片段 : .properties属性文件操作工具类 & JSON工具类

    摘要: 原创出处:www.bysocket.com 泥瓦匠BYSocket 希望转载,保留摘要,谢谢! “贵专” — 泥瓦匠 一.java.util.Properties API & 案例 j ...

  4. Json工具类 - JsonUtils.java

    Json工具类,提供Json与对象之间的转换. 源码如下:(点击下载 - JsonUtils.java . gson-2.2.4.jar ) import java.lang.reflect.Type ...

  5. Java json工具类,jackson工具类,ObjectMapper工具类

    Java json工具类,jackson工具类,ObjectMapper工具类 >>>>>>>>>>>>>>> ...

  6. Spring统一返回Json工具类,带分页信息

    前言: 项目做前后端分离时,我们会经常提供Json数据给前端,如果有一个统一的Json格式返回工具类,那么将大大提高开发效率和减低沟通成本. 此Json响应工具类,支持带分页信息,支持泛型,支持Htt ...

  7. 强大的Java Json工具类

    转自: https://blog.csdn.net/u014676619/article/details/49624165 import java.io.BufferedReader; import ...

  8. HttpClientUntils工具类的使用测试及注意事项(包括我改进的工具类和Controller端的注意事项【附 Json 工具类】)

    HttpClient工具类(我改过): package com.taotao.httpclient; import java.io.IOException; import java.net.URI; ...

  9. json工具类(三)——net包

    package com.ruoyi.common.utils.json; import java.util.List; import java.util.Map; import net.sf.json ...

随机推荐

  1. SQLHelper、DBUtil终极封装

    DBUtil.java package org.guangsoft.util; import java.io.InputStream; import java.sql.Connection; impo ...

  2. July 25th, Week 31st Monday, 2016

    We will not go quietly into the night. 今夜,我们将奋战到底. We will be the champion. We will not stop fightin ...

  3. 使用webstorm操作git

    0. 前言 在上一篇文章中,讲述了使用webstorm去调试node程序,最近研究了一下如何使用webstorm去操作git. 对于git的使用,大家的使用方式均有不同,最王道的方式非命令行莫属,基于 ...

  4. javascript中json解密

    一直以前都会断断续续会碰到js中的json数据的解析,下面凭着自己的经验,简单的讲解一下在js中的json的几种解析方法.  一.jquery的方式 首先你得先得到数据,一般都是jquery的ajax ...

  5. free(): invalid next size (fast/normal)问题

    本文转自 http://blog.sina.com.cn/s/blog_77f1e27f01019qq9.html  ,在此感谢! c++编译常会出现free(): invalid next size ...

  6. BaseActivity与BaseFragment的封装

    这篇博客主要是从BaseActivity与BaseFragment的封装开始,总结我们在实战开发中关于Fragment的注意事项以及心得体会. 先看以下效果图: 这里模拟的是用户登录模块,你可能会说, ...

  7. UML状态图和活动图

    UML状态图和活动图 统一建模语言UML(Unified Modeling Language)是非专利的第三代建模和规约语言.UML是一种开放的方法,用于说明.可视化.构建和编写一个正在开发的.面向对 ...

  8. php 克隆和引用类

    /*class Ren { public $name; public $sex; function __construct($n,$s) { $this->name=$n; $this-> ...

  9. error: Refusing to undefine while domain managed save image exists

    [root@ok libvirt]# virsh undefine win7 error: Refusing to undefine while domain managed save image e ...

  10. .NET生成word文档服务器配置常见问题

    注意:安装office2003的时候一定要选择 "完全安装" 而不是 "典型安装" 错误:System.Runtime.InteropServices.COME ...