[转载]C#利用Emit反射实现AOP,以及平台化框架封装思路 - 以利亚 - 博客园

baacloud免费翻墙vpn注册使用

[转载]C#利用Emit反射实现AOP,以及平台化框架封装思路 – 以利亚 – 博客园.

这是前两天扒的一段动态代理AOP代码,用的Emit反射生成子类来实现代理模式,在这里做个小笔记,然后讨论一下AOP框架的实现思路。

首先是主函数:

复制代码
        static void Main(string[] args)
        {
            RealClass proxy = (RealClass)DynamicProxyBuilder.Wrap(typeof(RealClass));
            proxy.Test();

            Console.ReadKey();
        }
复制代码

用一个动态代理Builder包装了真实的被代理类,这是被代理类:

复制代码
    public class RealClass
    {
        public RealClass() { }

        //必须是虚方法
        public virtual bool Test()
        {
            return false;
        }
    }
复制代码

我们需要在Test执行前后做一些事情,也就是拦截器,这里以一个布尔值为例子,随便一写:

复制代码
    public class Interceptor
    {
        public Object Call(String methodName, MulticastDelegate methodDelegate, params Object[] args)
        {
            Object obj = null;
            try
            {
                Console.WriteLine("进入拦截器,执行之前方法");

                obj = methodDelegate.Method.Invoke(methodDelegate.Target, args);
                if ((bool)obj)
                {
                    Console.WriteLine("返回真");
                }
                else
                {
                    Console.WriteLine("返回假");
                }

                Console.WriteLine("执行之后方法,离开拦截器");
            }
            catch (ApplicationException ex)
            {
                Console.WriteLine("出现异常");
            }

            return obj;
        }
    }
复制代码

即,在主函数里通过一个“框架API”调用这个类的代理子类来执行拦截器里的方法,DynamicProxyBuilder类代码如下:

View Code

这个程序在运行时会在bin下创建一个DynamicProxy.dll,里面是用Emit反射生成的代理子类,复写了父类的方法。

上面的代码里有一个Interceptor类,封装AOP框架的一个思路就是把这个类提出一个接口,里面有之前、之后、异常等方法,然后让一个抽象类实现这个接口,提供空实现骨架(模板方法模式),把这个抽象类注入到子类构造器当中来构造子类。

如果要结合项目造轮子的话,则允许以这个接口为标准二次开发具体的拦截器,并且可以根据需求封装配置界面,来配置针对系统当中哪一个具体操作命令来进行拦截。

DynamicProxyBuilder.Wrap这个方法可以封装为一个人性化的框架接口(作为AOP框架的API)来创建代理子类。

有必要将拦截器类放入IoC容器当中以防每次反射。

最后,动态代理性能很差,至少第一次生成dll很慢,而且看不懂!

真不想用框架、要自己写AOP的话,还是直接让最终执行核心方法的类实现拦截器接口,然后直接在自己的框架里调接口吧,这样还看得懂,别搞什么Emit!

最后引用马老师的一句经典语录——搞毛飞机啊!

赞(0) 打赏
分享到: 更多 (0)

觉得文章有用就打赏一下文章作者

支付宝扫一扫打赏

微信扫一扫打赏