用 java.lang.reflect.Proxy 制作类似AOP 的方法调用 Log 层

本文介绍如何利用Java反射机制中的Proxy类创建代理对象,实现类似AOP的效果来记录方法调用的日志,包括参数和返回值,有助于解决多人开发时因接口理解不一致带来的问题。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

java.lang.reflect.Proxy 制作类似AOP 的方法调用 Log 层
 
个人认为,java.lang.reflect.Proxy 简直是懒人必备的工具。
 
如,我负责编写一个分布式系统的一个服务,别的应用要调用我的服务的 RMI接口方法。而多人开发有着一个必然的缺点:每人负责的模块均对外提供接口,但事情往往会因为接口的定义者、实现者、使用者间对接口理解的偏差,而在软件的开发中引出不少麻烦。于是,接口调用日志就有作用了。特别是 RMI Interface 的日志。
 
import java.lang.reflect.InvocationHandler;
import java.lang.reflect.InvocationTargetException;
import java.lang.reflect.Method;
import java.lang.reflect.Proxy;
import java.text.MessageFormat;
import java.util.Arrays;
 
import org.apache.log4j.Level;
import org.apache.log4j.Logger;
 
 
/**
 *Afactoryofmethodinvokeloginterceptor.
 *logtheinvokeparamandresult.
 *@param<TargetInterface>
 */
publicclass InvokeLogProxyFactory<TargetInterface> {
   
    publicclass MyInvocationHandler implements InvocationHandler {
      
       private Level logLevel;
      
       private TargetInterface impl;
      
       public MyInvocationHandler(Level logLevel, TargetInterface impl) {
           this.logLevel = logLevel;
           this.impl = impl;
       }
 
       public Object invoke(Object proxy, Method method, Object[] args) throws Throwable {
           final Logger log = Logger.getLogger( impl.getClass() );
           String msg = MessageFormat.format( "Calling method {0}({1})", method.getName(), Arrays.toString( args ) );
           log.log( logLevel, msg );
           Object returnedResult = null;
           try {
               returnedResult = method.invoke( impl, args );
           } catch ( InvocationTargetException e ) {
              String msg1 = MessageFormat.format( "Call method[{0}]: catch exceptions:", method.getName() );
              log.log( logLevel, msg1, e.getCause() );
              throw e.getCause();
           } catch( Throwable e ) {
              log.error( "Runtime exception:", e );
              throw e;
           }
           log.log( logLevel, "returned val=" + returnedResult );
           return returnedResult;
       }
    }
   
    @SuppressWarnings("unchecked")
    public TargetInterface create(TargetInterface impl, Level logLevel) {
       MyInvocationHandler handler = new MyInvocationHandler( logLevel, impl);
         Object result = Proxy.newProxyInstance(impl.getClass().getClassLoader(),
                 impl.getClass().getInterfaces(),
                 handler);
         return (TargetInterface) result;     
    }
   
}
 
 
 
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值