有时候需要对已有的类进行前后加入一些操作,这样的需求通过代理类很容易实现,下面就是我实现一个对数据库连接进行的简单代理实现,达到对SQL进行监视的目的,其实这样的功能用第三方的控件很容易实现,这样做的目的就是学习而已;
需要代理的类:java.sql.Connection
import java.lang.reflect.InvocationHandler;
import java.lang.reflect.InvocationTargetException;
import java.lang.reflect.Method;
import java.lang.reflect.Proxy;
import java.sql.Connection;
import jxl.common.Logger;
import org.apache.commons.logging.Log;
import org.apache.commons.logging.LogFactory;
/**
* @author Xiaodong.Yue
*
*/
public class DebugConnection implements InvocationHandler {
private final static Log log = LogFactory.getLog(DebugConnection.class);
private Connection conn = null;
public DebugConnection(Connection conn) {
this.conn = conn;
}
/**
* Returns the conn.
* @return Connection
*/
public Connection getConnection(){
return (Connection) Proxy.newProxyInstance(conn.getClass().getClassLoader(), conn.getClass().getInterfaces(), this);
}
/* (non-Javadoc)
* @see java.lang.reflect.InvocationHandler#invoke(java.lang.Object, java.lang.reflect.Method, java.lang.Object[])
*/
public Object invoke(Object proxy, Method m, Object[] args)
throws Throwable {
try {
String method = m.getName();
// 对一些方法进行监视
if("prepareStatement".equals(method) ||"prepareCall".equals(method))
{
log.debug("[OEPSMWS-SQL] >>> " + args[0]);
}
return m.invoke(conn, args);
} catch (InvocationTargetException e) {
logger.error(e.getMessage());
throw e.getTargetException();
}
}
}
实现效果:
DEBUG - [OEPSMWS-SQL] >>> select id, name from profwork where parentid = ?
这样就可以达到自己定制的信息显示了,其他类似的场景很多,其实都可以通过这样的形式实现。
之后再要能把SQL参数加进去就好了,以后研究;