并不是很想寫這個(gè)系列,因?yàn)檫@個(gè)2pc單獨(dú)寫一個(gè)小架構(gòu)有點(diǎn)雞肋。不過也不知道寫什么了,先寫了再說吧。
整個(gè)流程如下圖:

關(guān)于AOP系列的文章很多,我這里也再重復(fù)造一下輪子。
首先,我們定義了一個(gè)IAopPRoxy,用于給AopProxyFactory用來創(chuàng)建Proxy實(shí)例的接口,代碼如下:

public interface IAopProxy { AopProxyBase CreateAopProxyInstance(MarshalByRefObject obj, Type type); }View CodeAOP截獲最重要的就是RealProxy類了,我們寫一個(gè)AopProxyBase抽象類,繼承于RealProxy,代碼如下:

public abstract class AopProxyBase : RealProxy { private readonly MarshalByRefObject target; //默認(rèn)透明代理 public AopProxyBase(MarshalByRefObject obj, Type type) : base(type) { this.target = obj; } public override IMessage Invoke(IMessage msg) { IMethodCallMessage call = (IMethodCallMessage)msg; bool isIntercept = false; var attrs = call.MethodBase.GetCustomAttributes(typeof(AopMethodAttribute), false) as AopMethodAttribute[]; //如果標(biāo)記了AopMethodAttribute的,才記錄。 if (attrs.Length > 0) { isIntercept = true; } if (isIntercept) { this.Before(msg, attrs); } //如果觸發(fā)的是構(gòu)造函數(shù),此時(shí)target的構(gòu)建還未開始 IConstructionCallMessage ctor = call as IConstructionCallMessage; if (ctor != null) { //獲取最底層的默認(rèn)真實(shí)代理 RealProxy default_proxy = RemotingServices.GetRealProxy(this.target); default_proxy.InitializeServerObject(ctor); MarshalByRefObject tp = (MarshalByRefObject)this.GetTransparentProxy(); return EnterpriseServicesHelper.CreateConstructionReturnMessage(ctor, tp); } IMethodReturnMessage result_msg = RemotingServices.ExecuteMessage(this.target, call); if (isIntercept) { this.After(msg, result_msg, attrs); } return result_msg; } public abstract void Before(IMessage requestMsg, AopMethodAttribute[] attrs); public abstract void After(IMessage requestMsg, IMessage Respond, AopMethodAttribute[] attrs); }View Code同時(shí),我們定義了AopAttribute : ProxyAttribute,代碼如下:

[AttributeUsage(AttributeTargets.Class)] public class AopAttribute : ProxyAttribute { IAopProxy proxy; public AopAttribute(Type factoryType) { this.proxy = (IAopProxy)AopProxyFactory.CreateInstance(factoryType); } public override MarshalByRefObject CreateInstance(Type serverType) { MarshalByRefObject target = base.CreateInstance(serverType); AopProxyBase rp = this.proxy.CreateAopProxyInstance(target, serverType); return (MarshalByRefObject)rp.GetTransparentProxy(); } }View Code可以看到在AopAttribute的構(gòu)造函數(shù)里面,有通過Factory去創(chuàng)建被攔截的Class的實(shí)例,避免每次都去創(chuàng)建,我加了一個(gè)Dictionary作為Cache,代碼如下:

public class AopProxyFactory { private static AopProxyCache _proxyCollection; private static readonly object _syncObject = new object(); static AopProxyFactory() { lock (_syncObject) { if (_proxyCollection == null) { _proxyCollection = new AopProxyCache(); } } } public static IAopProxy CreateInstance(Type type) { return _proxyCollection[type]; } }public class AopProxyCache { public Dictionary<Type, IAopProxy> _proxys; private static readonly object _syncObject = new object(); public AopProxyCache() { lock (this) { if (_proxys == null) { _proxys = new Dictionary<Type, IAopProxy>(); } } } public void Add(Type type, IAopProxy proxy) { if (_proxys == null) throw new ArgumentNullException("proxys is not init"); lock (_syncObject) { this._proxys[type] = proxy; } } public IAopProxy Get(Type type) { IAopProxy proxy; if (this._proxys.ContainsKey(type)) { proxy = this._proxys[type]; } else { lock(_syncObject) { if (!this._proxys.ContainsKey(type)) { proxy = (IAopProxy)Activator.CreateInstance(type); this.Add(type, proxy); } else { proxy = this._proxys[type]; } } } return proxy; } public IAopProxy this[Type type] { get { return this.Get(type); } set { this.Add(type, value); } } }View Code那道這里Aop的基礎(chǔ)類就搭建完畢了,具體的攔截后,要做什么,則需要去繼承于我們的抽象類AopProxyBase,然后復(fù)寫After和Before去做一些攔截,記錄的工作。
新聞熱點(diǎn)
疑難解答
圖片精選
網(wǎng)友關(guān)注