Skip to content

Instantly share code, notes, and snippets.

@wendal
Last active August 29, 2015 14:01
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save wendal/24b019d39e7e75bb3b21 to your computer and use it in GitHub Desktop.
Save wendal/24b019d39e7e75bb3b21 to your computer and use it in GitHub Desktop.
演示对Dao接口的封装,解决常见的FieldFilter的匿名内部类困扰
package org.nutz.dao.util;
import java.lang.reflect.InvocationHandler;
import java.lang.reflect.InvocationTargetException;
import java.lang.reflect.Method;
import java.lang.reflect.Proxy;
import org.nutz.dao.Dao;
import org.nutz.dao.FieldFilter;
import org.nutz.dao.TableName;
import org.nutz.lang.Lang;
import org.nutz.trans.Molecule;
/**
* 扩展Dao的功能
* @author wendal(wendal1985@gmail.com)
*
*/
public class ExtDaos {
private static Class<?>[] iz = new Class<?>[]{Dao.class};
/**
* 创建一个带FieldFilter的Dao代理实例. 注意,为避免出错,生成的Dao对象不应该传递到其他方法去.
* @param dao 原始的Dao实例
* @param filter 字段过滤器
* @return 带FieldFilter的Dao代理实例
*/
public static Dao ext(Dao dao, FieldFilter filter) {
return ext(dao, filter, null);
}
/**
* 创建一个带TableName的Dao代理实例. 注意,为避免出错,生成的Dao对象不应该传递到其他方法去.
* @param dao 原始的Dao实例
* @param tableName 动态表名上下文
* @return 带TableName的Dao代理实例
*/
public static Dao ext(Dao dao, Object tableName) {
return ext(dao, null, tableName);
}
public static Dao ext(Dao dao, FieldFilter filter, Object tableName) {
if (tableName == null && filter == null)
return dao;
ExtDaoInvocationHandler handler = new ExtDaoInvocationHandler(dao, filter, tableName);
return (Dao) Proxy.newProxyInstance(dao.getClass().getClassLoader(), iz, handler);
}
}
class ExtDaoInvocationHandler implements InvocationHandler {
protected ExtDaoInvocationHandler(Dao dao, FieldFilter filter, Object tableName) {
this.dao = dao;
this.filter = filter;
this.tableName = tableName;
}
protected Dao dao;
protected FieldFilter filter;
protected Object tableName;
public Object invoke(Object proxy, final Method method, final Object[] args) throws Throwable {
final Molecule<Object> m = new ExtDaoMolecule(dao, method, args);
if (filter != null && tableName != null) {
TableName.run(tableName, new Runnable() {
public void run() {
filter.run(m);
}
});
return m.getObj();
}
if (filter != null)
filter.run(m);
else
TableName.run(tableName, m);
return m.getObj();
}
}
class ExtDaoMolecule extends Molecule<Object> {
protected Dao dao;
protected Method method;
protected Object args;
public ExtDaoMolecule(Dao dao, Method method, Object args) {
super();
this.dao = dao;
this.method = method;
this.args = args;
}
public void run() {
try {
setObj(method.invoke(dao, args));
}
catch (IllegalArgumentException e) {
throw Lang.wrapThrow(e);
}
catch (IllegalAccessException e) {
throw Lang.wrapThrow(e);
}
catch (InvocationTargetException e) {
throw Lang.wrapThrow(e.getTargetException());
}
}
}
// 尝试一下JDK8的写法
package org.nutz.plugins.dao;
import java.lang.reflect.InvocationHandler;
import java.lang.reflect.InvocationTargetException;
import java.lang.reflect.Method;
import java.lang.reflect.Proxy;
import org.nutz.dao.Dao;
import org.nutz.dao.FieldFilter;
import org.nutz.lang.Lang;
import org.nutz.trans.Molecule;
public class ExtDaos2 {
public static Dao ext(Dao dao, FieldFilter filter) {
Proxy.newProxyInstance(dao.getClass().getClassLoader(), new Class<?>[]{Dao.class}, (obj, method, _args)-> {
Object[] re = new Object[1];
filter.run(()-> {
try {
re[0] = method.invoke(dao, _args);
} catch (InvocationTargetException e) {
throw Lang.wrapThrow(e.getTargetException());
} catch (Exception e2) {
throw Lang.wrapThrow(e2);
}
});
return re[0];
});
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment