這兩天寫 ASP.Net 寫暈了,老想偷點懶。由於在後台的代碼裡幾乎每個方法裡都要 try..catch 這麼來一遍,感覺很煩瑣。又聯想到 AOP, 但 AOP 的做法相對比較復雜,做法也很多。比如用 Dynamic Proxy, Attribute, 或者 Emit 等。我忽然聯想到了 C# 2.0 的新特性匿名委托,覺得這個雖然丑一點。。。不過其實也可以比較輕量級的簡單模擬 AOP 的效果:
// ASP.Net 裡面強制做一個頁面基類的要求是不過分的。。。
public partial class TestLogger: PageBase {
protected void Page_Load(object sender, EventArgs e) {
// 這個方法實現在頁面基類裡面,可以往裡面實現通用的異常處理,日志邏輯等。
TryDo(
// 這個裡面干實際的事情
delegate() {
int a = 1;
int b = 0;
int c = a / b;
},
// 這是一個可選的異常處理,如果傳遞一個 null 就會干脆忽略異常
delegate() {
Response.Write("Sorry, 發生了一個錯誤。");
}
);
}
}
在頁面基類裡面的實現代碼就很簡單了,也可以方便的統一管理。這裡我假定僅僅簡單的用 log4net 來對異常做日志記錄:
using System;
using System.Web.UI;
using log4net;
namespace SomeNamespace {
// 定義一個簡單的委托用於傳遞匿名委托
public delegate void MyAction();
// 定義頁面基類
public class PageBase : Page {
protected ILog logger;
// 頁面基類裡面集中處理所有異常處理邏輯
protected void TryDo(MyAction doHandler, MyAction exceptHandler) {
try {
// 干點兒實際的事情
doHandler();
} catch (Exception ex) {
// 簡單的記錄異常
logger.Error(ex);
// 其他一些處理
&n
bsp; // 。。。
// 調用自定義的異常處理,這裡沒有回傳 Exception 的具體信息。因為反正沒有必要對用戶顯示了。。。
if (exceptHandler != null)
exceptHandler();
}
}
protected override void OnInit(EventArgs e) {
// 初始化 logger. 正好這裡 GetType() 可以取到子類的實際類型
logger = LogManager.GetLogger(this.GetType());
base.OnInit(e);
}
}
}
好了,先寫到這裡。這只是我的一個簡單想法。目的在輕量級的實現異常或日志的集中管理。當然這個和完整的 AOP 概念是沒法比的,不過話說回來,好像目前在 .Net 中還沒有很完美的 AOP framework.
http://www.cnblogs.com/RChen/archive/2006/11/16/ASPnet_exception_handling.Html