天天看点

MSBuild + MSILInect实现编译时AOP之预览

class diagram:

MSBuild + MSILInect实现编译时AOP之预览

1:imethodinject:interface,拥有executeing,exceptioned,executesuccess三个契约为别为执行前,异常,成功。它们都有公同的参数类型:methodexecutioneventargs

MSBuild + MSILInect实现编译时AOP之预览

    executeing:返回值为bool类型,将决定是否继续执行方法体。exceptioned:属性eeption代表发生的异常信息,返回值exceptionstrategy(取值:handle, rethrow, thrownew)决定异常处理机制,handle已处理并忽略,rethrow重新抛出,thrownew抛出一个包装后的来源于methodexecutioneventargs 的exception。executesuccess,对于拥有返回值的方法,可以修改methodexecutioneventargs 的returnvalue,修改返回值。最后methodexecutioneventargs的order决定多个attribute的注入先后,即方法截获的先后顺序。

1:methodinterceptbase:针对于方法attribute标签,实现方法截获

MSBuild + MSILInect实现编译时AOP之预览
MSBuild + MSILInect实现编译时AOP之预览

[attributeusage(attributetargets.method, inherited = false, allowmultiple = false)]

    public class methodinterceptbase : attribute, imethodinject

    {

        public int order

        {

            get;

            set;

        }

        #region imethodinject members

        public virtual bool executeing(methodexecutioneventargs args)

            return true;

        public virtual exceptionstrategy exceptioned(methodexecutioneventargs args)

            return exceptionstrategy.rethrow;

        public virtual void executesuccess(methodexecutioneventargs args)

        #endregion

}

MSBuild + MSILInect实现编译时AOP之预览

2:matchedmethodinterceptbase:和上面方法之上的methodinterceptbase大体一致,区别在于其应用于class之上,属性rule为截获方法匹配(应用于多个方法之上相同截获),支持*匹配。

MSBuild + MSILInect实现编译时AOP之预览
MSBuild + MSILInect实现编译时AOP之预览

[attributeusage(attributetargets.class, inherited = false, allowmultiple = false)]

    public class matchedmethodinterceptbase : attribute, imethodinject

        public string rule

    }

MSBuild + MSILInect实现编译时AOP之预览

3:propertyinterceptbase:实现属性的注入,其属性action(enum propertyinterceptaction:none get, set)指注入属性的get或者set; 

MSBuild + MSILInect实现编译时AOP之预览
MSBuild + MSILInect实现编译时AOP之预览

[attributeusage(attributetargets.property, inherited = false, allowmultiple = false)]

    public class propertyinterceptbase : attribute, imethodinject

        public propertyinterceptaction action

MSBuild + MSILInect实现编译时AOP之预览

其上默认都是executeing继续执行,exceptioned为抛出不处理,成功不修改result。

下面是一个简单测试code:

MSBuild + MSILInect实现编译时AOP之预览
MSBuild + MSILInect实现编译时AOP之预览

using system;

using system.collections.generic;

using system.linq;

using system.text;

using system.reflection;

using green.aop;

namespace test

{   

    // [testaop2attribute(rule = "testmethod1*")]

    public class class1

        // [testaoppropertyattribute(action = propertyinterceptaction.set)]

        [testaoppropertygetattribute(action = propertyinterceptaction.get)]

        public teststrust testproperty

        [obsolete()]

        public static void main(string[] args)

        {          

            try

            {

                var y = new class1();

                // y.testproperty = datetime.now;

                console.writeline(y.testproperty);

            }

            catch (exception ex)

                console.writeline(ex.tostring());

            // new class1().testmethod1(1, 2, null);

            console.read();

            //throw new exception("exfffffffffffffffffffff");

        //[testaopattribute(order=1)]

        //[testaop1attribute(testproperty = 1, template = "sdsdsd",order=0)]

        public class1 testmethod1(int i, int j, class1 c)

            console.writeline("ok");

            return new class1();

    public class testaoppropertygetattribute : green.aop.propertyinterceptbase

        public override bool executeing(green.aop.methodexecutioneventargs args)

            console.writeline("------------------" + args);

            console.writeline(args.instance);

            console.writeline(args.method);

            console.writeline(this.gettype() + ":" + "executeing");

        public override green.aop.exceptionstrategy exceptioned(green.aop.methodexecutioneventargs args)

            console.writeline(this.gettype() + ":" + "exceptioned");

            return green.aop.exceptionstrategy.rethrow;

        public override void executesuccess(green.aop.methodexecutioneventargs args)

            console.writeline("-----------");

            console.writeline(this.gettype() + ":" + "executesuccess" + "--result:" + args.returnvalue);

    public class testaoppropertyattribute : green.aop.propertyinterceptbase

            return green.aop.exceptionstrategy.handle;

       {

            console.writeline(this.gettype() + ":" + "executesuccess");

    public class testaop2attribute : green.aop.matchedmethodinterceptbase

        public bool match(system.reflection.methodbase method)

    //[attributeusage(attributetargets.method)]

    public class testaopattribute : green.aop.methodinterceptbase

    [attributeusage(attributetargets.method)]

    public class testaop1attribute : attribute, green.aop.imethodinject

        public int testproperty

        public string template

        public bool executeing(green.aop.methodexecutioneventargs args)

        public green.aop.exceptionstrategy exceptioned(green.aop.methodexecutioneventargs args)

        public void executesuccess(green.aop.methodexecutioneventargs args)

MSBuild + MSILInect实现编译时AOP之预览

 注意测试有两种方式(由于没有安装包):

1:先重编译测试项目,运行consoleapplication2(在属性中修改控制台其实参数)。在查看测试项目。

在后续将会从简单demo分析实现原理。