java使用动态代理来实现AOP(日志记录)的实例代码
下面是一个AOP实现的简单例子:
首先定义一些业务方法:
/**
* Created with IntelliJ IDEA.
* Author: wangjie email:tiantian.china.2@gmail.com
* Date: 13-9-23
* Time: 下午3:49
*/
public interface BussinessService {
public String login(String username, String password);
public String find();
}
public class BussinessServiceImpl implements BussinessService {
private Logger logger = Logger.getLogger(this.getClass().getSimpleName());
@Override
public String login(String username, String password) {
return "login success";
}
@Override
public String find() {
return "find success";
}
}
/**
* Created with IntelliJ IDEA.
* Author: wangjie email:tiantian.china.2@gmail.com
* Date: 13-9-24
* Time: 上午10:27
*/
public interface WorkService {
public String work();
public String sleep();
}
public class WorkServiceImpl implements WorkService{
@Override
public String work() {
return "work success";
}
@Override
public String sleep() {
return "sleep success";
}
}
实现InvocationHandler接口,使用map来存储不同的InvocationHandler对象,避免生成过多。
package com.wangjie.aoptest2.invohandler;
import java.lang.reflect.InvocationHandler;
import java.lang.reflect.Method;
import java.lang.reflect.Proxy;
import java.util.Arrays;
import java.util.HashMap;
import java.util.logging.Logger;
/**
* Created with IntelliJ IDEA.
* Author: wangjie email:tiantian.china.2@gmail.com
* Date: 13-9-23
* Time: 下午3:47
*/
public class LogInvoHandler implements InvocationHandler{
private Logger logger = Logger.getLogger(this.getClass().getSimpleName());
private Object target; // 代理目标
private Object proxy; // 代理对象
private static HashMap<Class<?>, LogInvoHandler> invoHandlers = new HashMap<Class<?>, LogInvoHandler>();
private LogInvoHandler() {
}
/**
* 通过Class来生成动态代理对象Proxy
* @param clazz
* @return
*/
public synchronized static<T> T getProxyInstance(Class<T> clazz){
LogInvoHandler invoHandler = invoHandlers.get(clazz);
if(null == invoHandler){
invoHandler = new LogInvoHandler();
try {
T tar = clazz.newInstance();
invoHandler.setTarget(tar);
invoHandler.setProxy(Proxy.newProxyInstance(tar.getClass().getClassLoader(),
tar.getClass().getInterfaces(), invoHandler));
} catch (Exception e) {
e.printStackTrace();
}
invoHandlers.put(clazz, invoHandler);
}
return (T)invoHandler.getProxy();
}
@Override
public Object invoke(Object proxy, Method method, Object[] args) throws Throwable {
Object result = method.invoke(target, args); // 执行业务处理
// 打印日志
logger.info("____invoke method: " + method.getName()
+ "; args: " + (null == args ? "null" : Arrays.asList(args).toString())
+ "; return: " + result);
return result;
}
public Object getTarget() {
return target;
}
public void setTarget(Object target) {
this.target = target;
}
public Object getProxy() {
return proxy;
}
public void setProxy(Object proxy) {
this.proxy = proxy;
}
}
然后编写一个Test类测试:
/**
* Created with IntelliJ IDEA.
* Author: wangjie email:tiantian.china.2@gmail.com
* Date: 13-9-24
* Time: 上午9:54
*/
public class Test {
public static Logger logger = Logger.getLogger(Test.class.getSimpleName());
public static void main(String[] args) {
BussinessService bs = LogInvoHandler.getProxyInstance(BussinessServiceImpl.class);
bs.login("zhangsan", "123456");
bs.find();
logger.info("--------------------------------------");
WorkService ws = LogInvoHandler.getProxyInstance(WorkServiceImpl.class);
ws.work();
ws.sleep();
logger.info("--------------------------------------");
BussinessService bss = LogInvoHandler.getProxyInstance(BussinessServiceImpl.class);
bss.login("lisi", "654321");
bss.find();
}
}
以后需要添加新的业务逻辑XXXService,只需要调用
XXXService xs = LogInvoHandler.getProxyInstance(XXXServiceImpl.class);
即可。
也可以模仿Spring等框架的配置,把bean的类名配置在xml文件中,如:
<bean id="bussinessService" class="com.wangjie.aoptest2.service.impl.BussinessServiceImpl">
然后在java代码中解析xml,通过Class.forName("com.wangjie.aoptest2.service.impl.BussinessServiceImpl");获得Class对象
然后通过LogInvoHandler.getProxyInstance(Class.forName("com.wangjie.aoptest2.service.impl.BussinessServiceImpl"));获得代理对象Proxy
再使用反射去调用代理对象的方法。
运行结果如下:
九月 24, 2013 11:08:03 上午 com.wangjie.aoptest2.invohandler.LogInvoHandler invoke
INFO: ____invoke method: login; args: [zhangsan, 123456]; return: login success
九月 24, 2013 11:08:03 上午 com.wangjie.aoptest2.invohandler.LogInvoHandler invoke
INFO: ____invoke method: find; args: null; return: find success
九月 24, 2013 11:08:03 上午 com.wangjie.aoptest2.Test main
INFO: --------------------------------------
九月 24, 2013 11:08:03 上午 com.wangjie.aoptest2.invohandler.LogInvoHandler invoke
INFO: ____invoke method: work; args: null; return: work success
九月 24, 2013 11:08:03 上午 com.wangjie.aoptest2.invohandler.LogInvoHandler invoke
INFO: ____invoke method: sleep; args: null; return: sleep success
九月 24, 2013 11:08:03 上午 com.wangjie.aoptest2.Test main
INFO: --------------------------------------
九月 24, 2013 11:08:03 上午 com.wangjie.aoptest2.invohandler.LogInvoHandler invoke
INFO: ____invoke method: login; args: [lisi, 654321]; return: login success
九月 24, 2013 11:08:03 上午 com.wangjie.aoptest2.invohandler.LogInvoHandler invoke
INFO: ____invoke method: find; args: null; return: find success
java使用动态代理来实现AOP(日志记录)的实例代码相关推荐
- 了解动态代理:Spring AOP基础
为什么选择AOP: 要了解AOP(面向方面的编程),我们需要了解软件开发中的"横切关注点". 在每个项目中,都有一定数量的代码在多个类,多个模块中重复执行,例如几乎所有类和所有 ...
- 设计模式总结——代理模式以及java的动态代理
定义 给目标对象一个代理对象,并由代理对象控制对目标对象的引用.联想到生活中就像是海外代购 既然是代理,就说明他要做的事情要比你直接去做要做的多,这就联系到了方法的增强,也就联系到了AOP,面向切面. ...
- 看完Java的动态代理技术——Pythoner笑了
Java的动态代理常用来包装原始方法调用,用于增强或改写现有方法的逻辑,它在Java技术领域被广为使用,在阿里的Sofa RPC框架序列化中你能看到它的身影,Hibernate的实体类功能增强也是以动 ...
- 深入理解Java反射+动态代理,java开发面试笔试题
我总结出了很多互联网公司的面试题及答案,并整理成了文档,以及各种学习的进阶学习资料,免费分享给大家. 扫描二维码加VX好友,拉你进[程序员面试学习交流群]免费领取.也欢迎各位一起在群里探讨技术. 答: ...
- 4种实例 advice aop_JAVA动态代理 和 Spring AOP 4种通知的简单实现
学习Spring AOP 之前,先要了解下JAVA的动态代理.如果不清楚动态代理的概念就百度一下吧.废话不多说,直接上代码. 我们模拟一个简单的登录 首先我们创建一个用户登录的接口 package c ...
- [Java|面试] 面试被问Java的动态代理机制,能说说吗
Java的动态代理机制 文章目录 Java的动态代理机制 0. 什么是代理 1.动态代理和静态代理的区别 2. 使用代理的情况 3. 动态代理的构成 4. JDK中的动态代理 5. 手写一个JDK动态 ...
- 使用动态代理实现用AOP对数据库进行操作
使用动态代理实现用AOP对数据库进行操作 2008-03-14 11:04 作者:reverocean 来源:赛迪网 [摘要] 要实现对数据库的操作,离不开数据源(DataSource)或者连接(Co ...
- java的动态代理机制详解
2019独角兽企业重金招聘Python工程师标准>>> 参考资料 1.java的动态代理机制详解 转载于:https://my.oschina.net/Howard2016/blog ...
- 代理模式及Java实现动态代理
代理模式 定义:给某个对象提供一个代理对象,并由代理对象控制对于原对象的访问,即客户不直接操控原对象,而是通过代理对象间接地操控原对象. 代理模式UML图 在上图中: RealSubject 是原对象 ...
最新文章
- 20100506 学习记录:grdview添加新的一行数据
- 基于SSM实现的民宿网站系统
- Spark 1.4连接mysql诡异的问题及解决
- java paint文字_Java中paint怎么用
- 紫东太初:自动化所开源图-文-音三模态的预训练大模型
- php对象怎么拆分字符串数组,在PHP中将字符串拆分为Unicode字符数组的最佳方法是什么?...
- 结合随机微分方程,多大Duvenaud团队提出无限深度贝叶斯神经网络
- java g1 收集调优_Java性能调优:充分利用垃圾收集器
- Python基础入门_5面向对象基础
- Axure5.1不能输入中文问题.
- Flutter异步编程async与await的基本使用
- Chef宣布100%开源,要走红帽模式?\n
- loss函数之MultiMarginLoss, MultiLabelMarginLoss
- ubuntu14.04中安装open jdk1.8以及报错解决分析
- python unittest接口测试_Python+unittest 接口自动化测试
- 矢量数据空间索引之R树索引
- 2015-5-10分享的PDF
- 博士申请 | 上海交通大学自然科学研究院洪亮教授招收深度学习方向博士生
- sensor gyro_3d not found
- 信号与系统笔记 拉普拉斯变换的性质