您好,登錄后才能下訂單哦!
PostSharp 這個靜態植入的aop框架我就不多說了,在以前的aop文件,我們也嘗試用MSBuild+Mono.Cicel理解靜態植入AOP的原理。最近公司準備購買Postsharp做一些AOP,減少開發是代碼量,至于選擇AOP相信也不用多說。我也在今天重新了解了些Postsharp最新版更新,這陣子的博客更新也少了,所以準備在MSBuild+Mono.Cicel的基礎上再一些Postsharp系列。今天既然是初見,那么我們就從最簡單的OnExceptionAspect開始。
一:OnExceptionAspect
起定義如下:
先寫Aspect Attribute:
- View Code
- [Serializable]
- public class ExceptionAspectDemoAttribute : OnExceptionAspect
- {
- public override void OnException(MethodExecutionArgs args)
- {
- var msg = string.Format("時間[{0:yyyy年MM月dd日 HH時mm分}]方法{1}發生異常: {2}\n{3}", DateTime.Now, args.Method.Name, args.Exception.Message, args.Exception.StackTrace);
- Console.WriteLine(msg);
- args.FlowBehavior = FlowBehavior.Continue;
- }
- public override Type GetExceptionType(System.Reflection.MethodBase targetMethod)
- {
- return typeof(NullReferenceException);
- }
- }
- 復制代碼
注意Postsharp的Aspect都需要標記為可序列化的,因為在編譯時會為我們二進制序列化為資源,減少在運行是的開銷,這個將在后面專門講。
上面的code繼承至OnExceptionAspect,并且override OnException和GetExceptionType,GetExceptionType為我們需要處理的特定異常。OnException為異常處理決策方法。我們的異常處理決策是當NullReferenceException時候我們會記錄日志,并且方法指定繼續(args.FlowBehavior = FlowBehavior.Continue)。
看看我們的測試代碼:
- View Code
- class Program
- {
- static void Main(string[] args)
- {
- Program.ExceptionAspectDemoAttribute1();
- Program.ExceptionAspectDemoAttribute2();
- Console.Read();
- }
- [ExceptionAspectDemo]
- public static void ExceptionAspectDemoAttribute1()
- {
- string s = null;
- s.GetType();
- }
- [ExceptionAspectDemo]
- public static void ExceptionAspectDemoAttribute2()
- {
- throw new Exception("exception");
- }
- }
- 復制代碼
很顯然我們的兩個方法拋出了null異常和自定義異常,預期是NullReferenceException會被撲捉,而自定義異常會中斷,運行效果如下:
我們在來看看postsharp為我們做了什么,當然是反編譯看看:
二:Postsharp的Multicasting
1:Multicasting class:
在這隨便也說一下postsharp的Multicasting,多播這樣翻譯感覺有點死板呵呵,理解就行。利用這一點我們可以吧我們的aspect放在class,assembly等目標上匹配我們的多個目標。比如現在我們不想在我們的每個方法上加attribute,那我們可以選擇在class上,如:
反編譯,同樣注入了我們每個方法:
2:Multicasting assembly:
我們同樣可以利用
[assembly: PostSharpDemo.ExceptionAspectDemoAttribute()]
標記在我們的程序集上。
3:AttributeExclude:
但是注意這樣也標記了我們的aspect,某些時候可能會導致堆棧溢出 ,我們可以用AttributeExclude=true來排除。
同時我們也可以設置應用目標:AttributeTargetMemberAttributes是一個枚舉類型,定義如下:
比如我們需要過濾編譯時候生成的目標(自動屬性,action等等),
4:AttributePriority:
還有AttributePriority,我們可以設置編譯時優先級。如果我們對目標標記了多個aspect,這樣postsharp就不確定注入先后順序,這樣不能確保正確性,在vs編譯時候我們會看見警告:Their order of execution is undeterministic.
這是時候AttributePriority就派上用途了來決定我們植入的先后優先級。
5:其他匹配
同上AttributeTargetMemberAttributes 我們還可以利用AttributeTargetMembers,AttributeTargetTypes進行目標名稱的匹配,支持模糊匹配。
附件:Demo下載
我的AOP資料:
免責聲明:本站發布的內容(圖片、視頻和文字)以原創、轉載和分享為主,文章觀點不代表本網站立場,如果涉及侵權請聯系站長郵箱:is@yisu.com進行舉報,并提供相關證據,一經查實,將立刻刪除涉嫌侵權內容。