Spring系列(3/4)----一個較為完善的模型(完)
接上一篇,我們繼續來完善這個模型,我們為附加責任類定義了一個介面,這樣,只要實現這個介面的類都可以註冊,接收代理類的呼叫通知;同時為了更好的互動,我們還定義了一個呼叫引數介面,和一個具體的呼叫引數類,接下來,我們再看看代理類:
/// <summary>
/// 代理類,從AClass繼承.
/// </summary>
public class ProxyAClass1 : AClass
{
private AClass _target;
public Dictionary<IMethodExecNotify,MethodSubjectType> _observers = null;
/// <summary>
/// 建構函式,需傳入目標類例項.
/// </summary>
/// <param name="target"></param>
public ProxyAClass1(AClass Target)
{
_target = Target;
_observers = new Dictionary<IMethodExecNotify,MethodSubjectType>();
}
public void RegisterOberver(IMethodExecNotify Observer,MethodSubjectType)
{
//.........
}
public void RemoveOberver(IMethodExecNotify Observer)
{
//..........
}
/// <summary>
/// 執行方法例項.
/// </summary>
public override void Save()
{
object theRet = null;
try
{
MethodInfo theMI = _target.GetType().GetMethod("Save",new Type[]{});
var theAs = from item in _observers
where item.Value==MethodSubjectType.A
select item.Key;
foreach(var item in theAs)
{
object[] theParams = new object[]{};
IMethodInvocation theInvocation = new NotifyInvocation(_target,theMI,theParams);
item.SubjectMethodExecuting(theInvocation);
}
bool CanExecuteTargetMethod = true;
var theBs = from item in _observers
where item.Value==MethodSubjectType.B1
select item.Key;
foreach(var item in theBs)
{
object[] theParams = new object[]{};
IMethodInvocation theInvocation = new NotifyInvocation(_target,theMI,theParams);
CanExecuteTargetMethod = CanExecuteTargetMethod && bool.Parse(item.SubjectMethodExecuting(theInvocation).ToString());
if(CanExecuteTargetMethod==true)
{
theRet = _target.Save();
//.......
}
//.....
return theRet;
}
catch
{
//.......
}
finally
{
//......
}
}
}
上面的呼叫比較複雜,實際應用可能不需要分這麼多切入點。對於可以阻止目標類方法執行的邏輯(紅色程式碼部分),可以根據自己的需要來決定如何決策。
但目前這個代理類作為一個靜態示例還是可以的,但要作為動態代理類,跟前面的最初的代理原型一樣,無法使用,因為註冊管理功能無法使用,編譯上過不去,如果採用反射來呼叫,是可以,但每次都這樣使用,很麻煩。當然,這個改善很容易,只要將觀察者類集合作為引數在建構函式中傳遞進去就可以了。但註冊管理的責任誰來負責呢?我們前面分析過,因為代理類需要動態生成,而且動態代理類的形式和邏輯基本都一致,也適合動態生成,為了使用方便,我們可以提供一個工廠類來專門負責這件事情。那麼自然而然,觀察者註冊管理的功能也自然由其完成,代理類工廠在構造代理類的時候,再將觀察者集合作為建構函式的引數傳入代理類,當然,觀察者的通知執行還是由代理類來完成。而代理類工廠就是這個系列中第1篇中提到MyProxyFactory類的作用。
到這裡,面向AOP程式設計的動態代理模型就基本成型了,當然,還有許多地方可以改善,但原理如此,大家可以根據自己的需要去繼續改造。
下一篇,我們就來總結一下動態代理技術。