JAva:ダイナミックエージェント
動的エージェントとは?既存のオブジェクトを変更する方法、制御方法の実行、または前のアクティブな実行を実行した後に追加の操作を行います.特定のクラスProxyはnewProxyInstanceという方法で、指定したインタフェースエージェントのインスタンスを返します.
新ProxyInstance(クラス・ローダ、エージェントが実装するインタフェースを指定します.プロセッサ・オブジェクトは、エージェント・オブジェクトを呼び出す任意の方法でinvokeメソッドを呼び出します.この方法では追加の操作ができます)
Object invoke(Object proxj,Method,Object[]arg 0)-エージェントオブジェクト-エージェントを実装する方法-メソッドパラメータ-戻り値がこのメソッドで返されるもののインスタンス
新ProxyInstance(クラス・ローダ、エージェントが実装するインタフェースを指定します.プロセッサ・オブジェクトは、エージェント・オブジェクトを呼び出す任意の方法でinvokeメソッドを呼び出します.この方法では追加の操作ができます)
Object invoke(Object proxj,Method,Object[]arg 0)-エージェントオブジェクト-エージェントを実装する方法-メソッドパラメータ-戻り値がこのメソッドで返されるもののインスタンス
package com.twj.util;
import java.lang.reflect.InvocationHandler;
import java.lang.reflect.Method;
import java.lang.reflect.Proxy;
import java.sql.Connection;
import java.sql.SQLException;
import javax.sql.DataSource;
import org.apache.commons.dbutils.DbUtils;
import com.mchange.v2.c3p0.ComboPooledDataSource;
public class TransactionManager {
private TransactionManager() {
}
//-- ,
private static DataSource source = new ComboPooledDataSource();
//--
private static ThreadLocal<Boolean> isTran_local = new ThreadLocal<Boolean>(){
@Override
protected Boolean initialValue() {
return false;//-- false,
}
};
//-- , close
private static ThreadLocal<Connection> proxyConn_local = new ThreadLocal<Connection>(){};
//--
private static ThreadLocal<Connection> realconn_local = new ThreadLocal<Connection>(){};
/** * * @throws SQLException */
public static void startTran() throws SQLException{
isTran_local.set(true);//-- true
final Connection conn = source.getConnection();//-- , conn
conn.setAutoCommit(false);//--
realconn_local.set(conn);//-- ,
//-- sql, sql , sql , close ,
Connection proxyConn = (Connection) Proxy.newProxyInstance(conn.getClass().getClassLoader(), conn.getClass().getInterfaces()
, new InvocationHandler(){
public Object invoke(Object proxy, Method method,
Object[] args) throws Throwable {
if("close".equals(method.getName())){
return null;
}else{
return method.invoke(conn, args);
}
}
});
proxyConn_local.set(proxyConn);
}
/** * */
public static void commit(){
DbUtils.commitAndCloseQuietly(proxyConn_local.get());
}
/** * */
public static void rollback(){
DbUtils.rollbackAndCloseQuietly(proxyConn_local.get());
}
/** * : * , * , getConnection , Connection * @return * @throws SQLException */
public static DataSource getSource() throws SQLException{
if(isTran_local.get()){//-- , DataSource, getConnection Conn
return (DataSource) Proxy.newProxyInstance(source.getClass().getClassLoader(), source.getClass().getInterfaces()
,new InvocationHandler(){
public Object invoke(Object proxy, Method method,
Object[] args) throws Throwable {
if("getConnection".equals(method.getName())){
return proxyConn_local.get();
}else{
return method.invoke(source, args);
}
}
});
}else{//-- ,
return source;
}
}
/** * */
public static void release(){
DbUtils.closeQuietly(realconn_local.get());//-- release
realconn_local.remove();
proxyConn_local.remove();
isTran_local.remove();
}
}