<output id="qn6qe"></output>

    1. <output id="qn6qe"><tt id="qn6qe"></tt></output>
    2. <strike id="qn6qe"></strike>

      亚洲 日本 欧洲 欧美 视频,日韩中文字幕有码av,一本一道av中文字幕无码,国产线播放免费人成视频播放,人妻少妇偷人无码视频,日夜啪啪一区二区三区,国产尤物精品自在拍视频首页,久热这里只有精品12

      ASP.NET MVC集成EntLib實現“自動化”異常處理[實現篇]

      通過《實例篇》的實演示可以看出我們通過擴展實現的自動異常處理機制能夠利用EntLib的EHAB根據執行的一場處理策略對某個Action方法執行過程中拋出的異常進行處理。對于處理后的結果,則按照如下的機制對請求進行響應。[源代碼從這里下載][本文已經同步到《How ASP.NET MVC Works?》中]

      • 對于Ajax請求,直接創建一個用于封裝被處理后異常的數據對象,并據此創建一個JsonResult將異常信息回復給客戶端。
      • 對于非Ajax請求,如果當前Action方法上應用HandleErrorActionAttribute特性設置了匹配的Action方法用于處理該方法拋出的異常,那么執行該方法并用返回的ActionResult對象響應當前請求。
      • 如果HandleErrorActionAttribute特性不曾應用在當前Action方法上,或者通過該特性指定的Action不存在,則將默認的錯誤View呈現出來作為多請求的響應。

      目錄
      一、ExceptionPolicyAttribute & HandleErrorActionAttribute
      二、實現在OnException方法中的異常處理邏輯
      三、將處理后的錯誤消息存放在HttpContext的Items中
      四、用于設置錯誤消息的ErrorMessageHandler

      一、ExceptionPolicyAttribute & HandleErrorActionAttribute

      所有的這些都是通過一個自定義的ExceptionFilter來實現的。不過我們并沒有定義任何的ExceptionFilter特性,而是將異常處理實現在一個自定義的ExtendedController基類中,對異常的自動處理實現在重寫的OnException方法中,不過在介紹該方法的邏輯之前我們先來看看定義在ExtendedController中的其他輔助成員。

         1: public class ExtendedController: Controller
         2: {
         3:     private static Dictionary<Type, ControllerDescriptor> controllerDescriptors = new Dictionary<Type, ControllerDescriptor>();
         4:     private static object syncHelper = new object();
         5:  
         6:     protected override void OnException(ExceptionContext filterContext)
         7:     {
         8:         //省略成員
         9:     }      
        10:     
        11:     //描述當前Controller的ControllerDescriptor
        12:     public ControllerDescriptor Descriptor
        13:     {
        14:         get
        15:         {
        16:             ControllerDescriptor descriptor;
        17:             if(controllerDescriptors.TryGetValue(this.GetType(), out descriptor))
        18:             {
        19:                 return descriptor;
        20:             }
        21:             lock (syncHelper)
        22:             {
        23:                 if (controllerDescriptors.TryGetValue(this.GetType(), out descriptor))
        24:                 {
        25:                     return descriptor;
        26:                 }
        27:                 else
        28:                 {
        29:                     descriptor = new ReflectedControllerDescriptor(this.GetType());
        30:                     controllerDescriptors.Add(this.GetType(), descriptor);
        31:                     return descriptor;
        32:                 }
        33:             }
        34:         }
        35:     }
        36:     //獲取異常處理策略名稱
        37:     public string GetExceptionPolicyName()
        38:     {
        39:         string actionName = ControllerContext.RouteData.GetRequiredString("action");
        40:         ActionDescriptor actionDescriptor = this.Descriptor.FindAction(ControllerContext, actionName);
        41:         if (null == actionDescriptor)
        42:         {
        43:             return string.Empty;
        44:         }
        45:         ExceptionPolicyAttribute exceptionPolicyAttribute = actionDescriptor.GetCustomAttributes(true).OfType<ExceptionPolicyAttribute>().FirstOrDefault()??               
        46:            Descriptor.GetCustomAttributes(true).OfType<ExceptionPolicyAttribute>().FirstOrDefault()?? new ExceptionPolicyAttribute("");
        47:         return exceptionPolicyAttribute.ExceptionPolicyName;
        48:     }
        49:  
        50:     //獲取Handle-Error-Action名稱
        51:     public string GetHandleErrorActionName()
        52:     {
        53:         string actionName = ControllerContext.RouteData.GetRequiredString("action");
        54:         ActionDescriptor actionDescriptor = this.Descriptor.FindAction(ControllerContext, actionName);
        55:         if (null == actionDescriptor)
        56:         {
        57:             return string.Empty;
        58:         }
        59:         HandleErrorActionAttribute handleErrorActionAttribute = actionDescriptor.GetCustomAttributes(true).OfType<HandleErrorActionAttribute>().FirstOrDefault()??          
        60:             Descriptor.GetCustomAttributes(true).OfType<HandleErrorActionAttribute>().FirstOrDefault()?? new HandleErrorActionAttribute("");
        61:         return handleErrorActionAttribute.HandleErrorAction;
        62:     }
        63:  
        64:     //用于執行Handle-Error-Action的ActionInvoker
        65:     public HandleErrorActionInvoker HandleErrorActionInvoker { get; private set; }
        66:  
        67:     public ExtendedController()
        68:     {
        69:         this.HandleErrorActionInvoker = new HandleErrorActionInvoker();
        70:     }
        71: }

      ExtendedController的Descriptor屬性用于返回描述自身的ControllerDescriptor對象,實際上是一個ReflectedControllerDescriptor對象。為了避免頻繁的反射操作造成對性能的影響,我們將基于某個類型解析出來的ReflectedControllerDescriptor對象進行了全局性緩存。

      GetExceptionPolicyName方法用于返回當前采用的異常處理策略名稱。異常處理策略名稱是通過具有如下定義的ExceptionPolicyAttribute特性來指定的。該特性既可以應用在Controller類型上,也可以應用在Action方法上,換句話說,我們可以采用不同的策略來處理從不同Action執行過程中拋出的異常。GetExceptionPolicyName利用ControllerDesctior和ActionDescriptor可以很容易地得到應用的ExceptionPolicyAttribute特性,進而得到相應的異常處理策略名稱。

         1: [AttributeUsage( AttributeTargets.Class| AttributeTargets.Method, AllowMultiple = false, Inherited = true)]
         2: public class ExceptionPolicyAttribute: Attribute
         3: {
         4:     public string ExceptionPolicyName { get; private set; }
         5:     public ExceptionPolicyAttribute(string exceptionPolicyName)
         6:     {
         7:         this.ExceptionPolicyName = exceptionPolicyName;
         8:     }
         9: }

      另一個方法GetHandleErrorActionName用于獲取通過應用在Action方法上的特性HandleErrorActionAttribute設置的Handle-Error-Action的名稱。該特性定義如下,它既可以應用于某個Action方法,也可以應用于Controller類。GetHandleErrorActionName方法同樣利用ControllerDesctior和ActionDescriptor得到應用的ExceptionPolicyAttribute特性,并最終得到對應的異常處理Action名稱。

         1: [AttributeUsage( AttributeTargets.Class| AttributeTargets.Method, AllowMultiple = false)]
         2: public class HandleErrorActionAttribute: Attribute
         3: {
         4:     public string HandleErrorAction { get; private set; }
         5:     public HandleErrorActionAttribute(string handleErrorAction = "")
         6:     {
         7:         this.HandleErrorAction = handleErrorAction;
         8:     }
         9: }

      通過HandleErrorActionAttribute特性設置的Handle-Error-Action需要手工執行以實現對當前請求的響應,為此我們創建了一個具有如下定義的HandleErrorActionInvoker。它是ControllerActionInvoker的子類,Handle-Error-Action需要手工執行以實現對當前請求的響應的執行通過虛方法InvokeActionMethod來完成。ExtendedController的HandleErrorActionInvoker返回的就是這樣一個對象。

         1: public class HandleErrorActionInvoker: ControllerActionInvoker
         2: {
         3:     public virtual ActionResult InvokeActionMethod(ControllerContext controllerContext, ActionDescriptor actionDescriptor)
         4:     {
         5:         IDictionary<string, object> parameterValues = this.GetParameterValues(controllerContext, actionDescriptor);
         6:         return base.InvokeActionMethod(controllerContext, actionDescriptor, parameterValues);
         7:     }
         8: }

      二、實現在OnException方法中的異常處理邏輯

      整個異常處理和最終對請求的相應實現在如下所示的OnException方法中,流程并不復雜,在這里就不一一贅述了。不過對于整個處理流程,有兩個點值得一提:其一,在調用EntLib的EHAB對異常處理過程中,允許相應的ExceptionHandler設置一個友好的錯誤消息,而這個消息被保存在當前HttpContext的Items中。其二,在調用異常處理方法之前,我們錯誤消息添加到當前的ModelState中,這也是為什么在上面的實例演示中錯誤消息會自動出現在ValidationSummary中的根本原因。

         1: public class ExtendedController: Controller
         2: {    
         3:     //其他成員
         4:     protected override void OnException(ExceptionContext filterContext)
         5:     {
         6:         //或者當前的ExceptionPolicy,如果不存在,則直接調用基類OnException方法
         7:         string exceptionPolicyName = this.GetExceptionPolicyName();
         8:         if (string.IsNullOrEmpty(exceptionPolicyName))
         9:         {
        10:             base.OnException(filterContext);
        11:             return;
        12:         }
        13:  
        14:         //利用EntLib的EHAB進行異常處理,并獲取錯誤消息和最后拋出的異常
        15:         filterContext.ExceptionHandled = true;
        16:         Exception exceptionToThrow;
        17:         string errorMessage;
        18:         try
        19:         {
        20:             ExceptionPolicy.HandleException(filterContext.Exception,exceptionPolicyName, out exceptionToThrow);
        21:             errorMessage = System.Web.HttpContext.Current.GetErrorMessage();
        22:         }
        23:         finally
        24:         {
        25:             System.Web.HttpContext.Current.ClearErrorMessage();
        26:         }
        27:         exceptionToThrow = exceptionToThrow ?? filterContext.Exception;
        28:  
        29:         //對于Ajax請求,直接返回一個用于封裝異常的JsonResult
        30:         if (Request.IsAjaxRequest())
        31:         {
        32:             filterContext.Result = Json(new ExceptionDetail(exceptionToThrow, errorMessage));
        33:             return;
        34:         }
        35:  
        36:         //如果設置了匹配的HandleErrorAction,則調用之;
        37:         //否則將Error View呈現出來
        38:         string handleErrorAction = this.GetHandleErrorActionName();
        39:         string controllerName = ControllerContext.RouteData.GetRequiredString("controller");
        40:         string actionName = ControllerContext.RouteData.GetRequiredString("action");
        41:         errorMessage = string.IsNullOrEmpty(errorMessage) ? exceptionToThrow.Message : errorMessage;
        42:         if (string.IsNullOrEmpty(handleErrorAction))
        43:         {
        44:             filterContext.Result = View("Error", new ExtendedHandleErrorInfo(exceptionToThrow, controllerName, actionName, errorMessage));
        45:         }
        46:         else
        47:         {
        48:             ActionDescriptor actionDescriptor = Descriptor.FindAction(ControllerContext, handleErrorAction);                
        49:             ModelState.AddModelError("", errorMessage);
        50:             filterContext.Result = this.HandleErrorActionInvoker.InvokeActionMethod(ControllerContext, actionDescriptor);
        51:         }
        52:     }      
        53: }

      三、將處理后的錯誤消息存放在HttpContext的Items中

      在調用EntLib的EHAB進行異常處理之后從當前HttpContext提取錯誤消息,以及最后清除消息分別是通過HttpContext的擴展方法GetErrorMessage和ClearErrorMessage實現的。如下面的代碼片斷所示,除了這兩個擴展方法我們還定義了另一個用于設置錯誤消息的SetErrorMessage方法。

         1: public static class HttpContextExtensions
         2: {
         3:     public static string keyOfErrorMessage = Guid.NewGuid().ToString();
         4:  
         5:     public static void SetErrorMessage(this HttpContext context, string errorMessage)
         6:     {
         7:         context.Items[keyOfErrorMessage]=errorMessage;
         8:     }
         9:  
        10:     public static string GetErrorMessage(this HttpContext context)
        11:     {
        12:         return context.Items[keyOfErrorMessage] as string;
        13:     }
        14:  
        15:     public static void ClearErrorMessage(this HttpContext context)
        16:     {
        17:         if (context.Items.Contains(keyOfErrorMessage))
        18:         {
        19:             context.Items.Remove(keyOfErrorMessage);
        20:         }            
        21:     }
        22: }

      四、用于設置錯誤消息的ErrorMessageHandler

      用于設置錯誤信息的ErrorMessageHandler以及對應配置元素類型ErrorMessageHandlerData定義如下。ErrorMessageHandler表示錯誤消息的ErrorMessage屬性在構造函數中被初始化,而在實現的HandleException方法中直接通過調用當前HttpContext的擴展方法SetErrorMessage進行錯誤消息的設置。

         1: [ConfigurationElementType(typeof(ErrorMessageHandlerData))]
         2: public class ErrorMessageHandler: IExceptionHandler
         3: {
         4:     public string ErrorMessage { get; private set; }
         5:     public ErrorMessageHandler(string errorMessage)
         6:     {
         7:         this.ErrorMessage = errorMessage;
         8:     }
         9:     public Exception HandleException(Exception exception, Guid handlingInstanceId)
        10:     {
        11:         if (null != HttpContext.Current)
        12:         {
        13:             HttpContext.Current.SetErrorMessage(this.ErrorMessage);
        14:         }
        15:         return exception;
        16:     }
        17: }
        18:  
        19: public class ErrorMessageHandlerData : ExceptionHandlerData
        20: {
        21:     [ConfigurationProperty("errorMessage", IsRequired=true)]
        22:     public string ErrorMessage
        23:     {
        24:         get { return (string)this["errorMessage"]; }
        25:         set { this["errorMessage"] = value; }
        26:     }
        27:  
        28:     public override IEnumerable<TypeRegistration> GetRegistrations(string namePrefix)
        29:     {
        30:         yield return new TypeRegistration<IExceptionHandler>(() => new ErrorMessageHandler(this.ErrorMessage))
        31:         {
        32:             Name = this.BuildName(namePrefix),
        33:             Lifetime = TypeRegistrationLifetime.Transient
        34:         };
        35:     }
        36: }

       

      ASP.NET MVC集成EntLib實現“自動化”異常處理[實例篇]
      ASP.NET MVC集成EntLib實現“自動化”異常處理[實現篇]

      posted @ 2012-08-08 08:25  Artech  閱讀(4824)  評論(7)    收藏  舉報
      主站蜘蛛池模板: 777米奇色狠狠俺去啦| 亚洲综合国产一区二区三区| 国产精品久久久国产盗摄| 日韩丝袜亚洲国产欧美一区| 成年女人喷潮免费视频| 国产精品久久国产三级国不卡顿 | 99久久精品国产熟女拳交| 欧美日韩精品一区二区视频| 精品无码国产自产拍在线观看蜜| 亚洲精品日本久久久中文字幕| 久久综合精品成人一本| 3d全彩无码啪啪本子全彩| 国产精品中文字幕第一页| 欧美国产精品啪啪| 亚洲午夜精品久久久久久抢| 日本中文字幕在线播放| 日韩熟女乱综合一区二区| 少妇高潮喷水惨叫久久久久电影| 色窝窝免费播放视频在线| 97视频精品全国免费观看| 国产永久免费高清在线观看| 无码人妻精品一区二区三区66| 久久综合伊人77777| 无码抽搐高潮喷水流白浆| 亚洲精品国偷自产在线99人热| 亚洲欧美日韩国产精品一区二区| 一区二区三区国产综合在线| а∨天堂一区中文字幕| а∨天堂一区中文字幕| 日韩av一区二区三区在线| 亚洲欧美成人久久综合中文网| 免费人成网站免费看视频| 少妇人妻精品无码专区视频| 无码国产成人午夜电影在线观看| 少妇人妻真实偷人精品| 亚洲高清国产自产拍av| 欧洲尺码日本尺码专线美国又| 中文字幕国产精品资源| 人人做人人妻人人精| 国产精品久久久久精品日日| 国产成人亚洲欧美二区综合|