首先要解決的問題是如何判斷使用者是否擁有調用某個操作的權限,這個判斷是由各個應用程式自己實作了,為了統一對權限的判斷,是以我們指定了接口IPermissionVerifier:
/// <summary>
/// IPermissionVerifier 用于驗證目前使用者對目标類的目标方法的調用權限是否足夠。
/// 如果需要使用Aop來進行權限管理,則要實作IPermissionVerifier接口。
/// </summary>
public interface IPermissionVerifier
{
bool QualifiedToOperation(object permissionNeeded ,string destClassFullName ,string destMethodName) ;
}
其中,permissionNeeded通過應用于方法的特性的參數指定(後面可以看到),destClassFullName表示目标方法所在class的全稱,destMethodName是目标方法名。
當使用者的權限不滿足條件時,對目标方法的調用将抛出PermissionLimittedException異常,該異常定義如下:
/// 當沒有權限的使用者調用某項操作時,将抛出此異常
[Serializable]
public class PermissionLimittedException : Exception
public PermissionLimittedException()
{
}
public PermissionLimittedException(string msg):base(msg)
{
public PermissionLimittedException(string msg ,Exception innerException) : base(msg ,innerException)
注意,自定義異常必須是可序列化的,這樣就可以保證異常通過remoting傳遞。
接下來,就可以實作權限方面PermissionAspect了。
/// PermissionAspect 權限方面,如果目前使用者不夠權限調用某個方法,則抛出PermissionLimittedException。
/// aspectClassArgument :實作了IPermissionVerifier接口的類型
/// aspectMethodArgument:操作所需的權限,由使用者自定義
public class PermissionAspect :IAspect
public PermissionAspect()
#region IAspect 成員
public void PreProcess(IMethodCallMessage requestMsg, object aspectClassArgument, object aspectMethodArgument)
Type verifierType = (Type)aspectClassArgument ;
Type destType = typeof(IPermissionVerifier) ;
if(! destType.IsAssignableFrom(verifierType))
{
throw new Exception("the PermissionVerifierType is invalid !") ;
}
IPermissionVerifier pmVerifier = (IPermissionVerifier)Activator.CreateInstance(verifierType) ;
if(pmVerifier == null)
object pmNeeded = aspectMethodArgument ;
string className = AopHelper.GetFullClassName(requestMsg) ;
string methodName = AopHelper.GetMethodName(requestMsg) ;
bool qualified = pmVerifier.QualifiedToOperation(pmNeeded ,className ,methodName) ;
if(! qualified)
throw new PermissionLimittedException(string.Format("Current user have no permission to call dest method : {0}.{1}!" ,className ,methodName)) ;
public void PostProcess(IMethodCallMessage requestMsg, ref IMethodReturnMessage respond, object aspectClassArgument, object aspectMethodArgument)
// TODO: 添加 PermissionAspect.EnterpriseServerBase.Aop.ComplexAop.IAspect.PostProcess 實作
#endregion
}
最後給出一個示例:
public class class1
[STAThread]
static void Main(string[] args)
try
Example exa = new Example() ;
exa.SayHello("sky") ;
exa.SayByebye("sky") ;
catch(Exception ee)
Console.WriteLine(ee.Message) ;
Console.Read() ;
[Aspect(typeof(PermissionAspectWrap))]
public class Example :ContextBoundObject
{
[AspectSwitcher(typeof(PermissionAspectWrap) ,true ,Permission.Common)]
public void SayHello(string name)
Console.WriteLine("Hello ," + name) ;
[AspectSwitcher(typeof(PermissionAspectWrap) ,true ,Permission.Super)] //調用此方法需要Permission.Super權限
public void SayByebye(string name)
Console.WriteLine("Byebye ," + name) ;
#region PermissionAspectWrap
public class PermissionAspectWrap :IAspectProcessorWrap
#region IAspectProcessorWrap 成員
public Type AspectProcessorType
get
{
return typeof(PermissionAspect);
public object AspectClassArgument
return typeof(PermissionVerifier) ;
public AspectSwitcherState DefaultAspectSwitcherState
return AspectSwitcherState.On ;
#endregion
#region PermissionVerifier ,Permission ,Logger
public class PermissionVerifier :IPermissionVerifier
private static int curPermission = Permission.Common ;
#region IPermissionVerifier 成員
public bool QualifiedToOperation(object permissionNeeded, string destClassFullName, string destMethodName)
int destPermission = (int)permissionNeeded ;
if(PermissionVerifier.curPermission > destPermission)
return true ;
return false;
public class Permission
public const int Common = 0 ;
public const int Super = 1 ;
#endregion
由于目前使用者級别為Permission.Common,是以在調用SayByebye的時候會抛出異常,而在調用SayHello的時候卻可以正常進行。