Spring学习笔记--AOP的简略实现(基于J2SE动态代理与CgLib)

基于j2se动态代理AOP实现

测试Bean

package com.wenj.services;

public interface TestBean {
	public void testBean();
}



package com.wenj.servicesimpl;

import com.wenj.services.TestBean;

public class TestBeanImpl implements TestBean {
	private String user;
	public TestBeanImpl(){}
	
	public TestBeanImpl(String user){
		this.user = user;
	}

	public void testBean() {
		// TODO Auto-generated method stub
		System.out.println("TestBean, User: " + user);
	}

	public String getUser() {
		return user;
	}
}


 

AOP切面

package com.wenj.aop;

 

import java.lang.reflect.InvocationHandler;

import java.lang.reflect.Proxy;

 

public class J2seProxyFactory implements InvocationHandler{

private Object obj;

public J2seProxyFactory(Object obj){

this.obj = obj;

}

public Object createProxyInstance(){

return Proxy.newProxyInstance(obj.getClass().getClassLoader(), 

obj.getClass().getInterfaces(), 

this);

}

 

@Override

public Object invoke(Object proxy, Method method, Object[] args)

throws Throwable {

TestBeanImpl tb = (TestBeanImpl)obj;

Object proxyObj = null;

if(tb.getUser() != null){

proxyObj = method.invoke(obj, args);

}

return proxyObj;

}

 

}

 

createProxyInstance()是创建代理对象的方法

invoke()为拦截点

obj对象为被代理对象

在拦截点还可以添加我们所需要的事件通知

测试

最后在jUnit测试单元添加如下测试代码:

@Test

public void testAop(){

J2seProxyFactory pf = new J2seProxyFactory(new TestBeanImpl());

TestBean tb = (TestBean)pf.createProxyInstance();

tb.testBean();

}

看以看到结果可以根据权限正常的拦截到TestBean执行方法如果将new TestBeanImpl()改为new TestBeanImpl(xxx)拦截器也可以正常的拦截到并且通过权限验证

 

基于CgLibAOP实现

测试Bean

 

package com.wenj.servicesimpl;

 

public class TestDAO {

private String name;

public TestDAO(){ }

public TestDAO(String name) {

this.name = name;

}

 

 

public String getName() {

return name;

}

 

 

public void setName(String name) {

this.name = name;

}

 

 

public void save(){

System.out.println(name + " invoke save()!");

}

}

 

切面

package com.wenj.aop;

 

import java.lang.reflect.Method;

 

import org.springframework.cglib.proxy.Enhancer;

import org.springframework.cglib.proxy.MethodInterceptor;

import org.springframework.cglib.proxy.MethodProxy;

 

import com.wenj.servicesimpl.TestDAO;

 

public class CgLibProxyFactory implements MethodInterceptor{

 

private Object targetObj;

public CgLibProxyFactory(Object targetObj){

this.targetObj = targetObj;

}

//生成代理对象

public Object getProxyObject(){

Object proxyObj = null;

Enhancer e = new Enhancer();

e.setSuperclass(targetObj.getClass());

e.setCallback(this);

proxyObj = e.create();

return proxyObj;

}

 

//切入点

@Override

public Object intercept(Object obj, Method method, Object[] args,

MethodProxy methodProxy) throws Throwable {

TestDAO td = (TestDAO)targetObj;

Object test = null;

if(null != td.getName()){

if("save" == method.getName()){

//拦截点

test = method.invoke(td, args);

System.out.println("ProxyObj invoke method save()!");//after advice()

}

}

return test;

}

}

 

最后在jUnit测试单元添加如下测试代码

@Test

public void testCgLibProxyFactory(){

CgLibProxyFactory cf = new CgLibProxyFactory(new TestDAO("aaa"));

TestDAO t = (TestDAO)cf.getProxyObject();

t.save();

}

 

结果能够正常的拦截Bean执行方法而且能够根据我们设定的权限来进行拦截

 

J2SE动态代理实现AOP有一个缺陷就是目标对象必须实现一个接口

所以对于没有实现接口的Bean来说得另想方法, 这里我借助一个第三方的类库CgLib, 这样使没有实现接口的类也能实现AOP的功能

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值