假设我们使用JDBC技术操作数据库时我们的步骤是
1、打开连接
2、执行语句
3、异常回滚
4、无异常正常执行
5、关闭资源
下面我们来看一个小例子的,细心的读者注意,如果我们将拦截器的实现方法里修改成对应的对数据库操作方法,那么我们在实际使用中,其他处理工作AOP按照约定的流程自动为我们完成了,我们就只需要执行SQL这一步,就能实现对数据库的操作
ProxyBeanFactory
package com.util;
import com.inf.Interceptor;
//用这样一个类生成对应的对象,获取bean和约定
public class ProxyBeanFactory {
public static <T> T getBean(T obj, Interceptor interceptor){
return (T) ProxyBeanUtil.getBean(obj, interceptor);
}
}
ProxyBeanUtil
package com.util;
import java.lang.reflect.InvocationHandler;
import java.lang.reflect.Method;
import java.lang.reflect.Proxy;
import com.inf.Interceptor;
class ProxyBeanUtil implements InvocationHandler {
//被代理对象
private Object obj;
//拦截器
private Interceptor interceptor = null;
/**
* 获取动态代理对象.
* @param obj 被代理对象
* @param interceptor 拦截器
* @param aroundFlag 是否启用around方法
* @return 动态代理对象
*/
public static Object getBean(Object obj, Interceptor interceptor) {
//使用当前类,作为代理方法,此时被代理对象执行方法的时候,会进入当前类的invoke方法里
ProxyBeanUtil _this = new ProxyBeanUtil();
//保存被代理对象
_this.obj = obj;
//保存拦截器
_this.interceptor = interceptor;
//生成代理对象,并绑定代理方法
return Proxy.newProxyInstance(obj.getClass().getClassLoader(),
obj.getClass().getInterfaces(), _this);
}
/**
* 代理方法.
* @param proxy 代理对象
* @param method 当前调度方法
* @param args 参数
* @return 方法返回
* @throws Throwable 异常
*/
@Override
public Object invoke(Object proxy, Method method, Object[] args) throws Throwable {
Object retObj = null;
//是否产生异常
boolean exceptionFlag = false;
//before方法
interceptor.before(obj);
try {
//反射原有方法
retObj = method.invoke(obj, args);
} catch (Exception ex) {
exceptionFlag = true;
} finally {
//after方法
interceptor.after(obj);
}
if (exceptionFlag) {
//afterThrowing方法
interceptor.afterThrowing(obj);
} else {
//afterReturning方法
interceptor.afterReturning(obj);
}
return retObj;
}
}
Interceptor接口
package com.inf;
//拦截接口
public interface Interceptor {
public void before(Object object);
public void after(Object object);
public void afterReturning(Object object);
public void afterThrowing(Object object);
}
Interceptor接口实现
package com.impl;
import com.inf.Interceptor;
public class InterceptorImpl implements Interceptor{
@Override
public void before(Object object) {
System.out.println("准备打印");
}
@Override
public void after(Object object) {
System.out.println("打印完成");
}
@Override
public void afterReturning(Object object) {
System.out.println("打印正常");
}
@Override
public void afterThrowing(Object object) {
System.out.println("打印异常");
}
}
Role这里还需要get和set方法
package com.entity;
public class Role {
private Long id;
private String roleName;
private String note;
public Role() {
}
public Role(Long id, String roleName,String note) {
this.id = id;
this.roleName = roleName;
this.note = note;
}
}
Role接口
package com.inf;
import com.entity.Role;
public interface RoleService {
public void printRole(Role role);
}
Role接口实现
package com.impl;
import com.entity.Role;
import com.inf.RoleService;
public class RoleServiceImpl implements RoleService{
@Override
public void printRole(Role role) {
System.out.println(role.getId()+"__"+role.getRoleName()+"__"+role.getNote()+"__");
}
}
test
package com.test;
import com.entity.Role;
import com.impl.InterceptorImpl;
import com.impl.RoleServiceImpl;
import com.inf.Interceptor;
import com.inf.RoleService;
import com.util.ProxyBeanFactory;
public class Test {
public static void main(String[] args) {
RoleService roleService = new RoleServiceImpl();
Interceptor interceptor = new InterceptorImpl();
//约定获取bean方法
RoleService proxy = ProxyBeanFactory.getBean(roleService, interceptor);
Role role = new Role(1L,"张三","zs");
proxy.printRole(role);
System.out.println("测试 afterThrowing 方法");
role = null;
proxy.printRole(role);
}
}
运行结果中,我们联系数据库操作,准备打印——打开数据库,打印正常——关闭连接,打印异常——回滚事务