Java自学者论坛

 找回密码
 立即注册

手机号码,快捷登录

恭喜Java自学者论坛(https://www.javazxz.com)已经为数万Java学习者服务超过8年了!积累会员资料超过10000G+
成为本站VIP会员,下载本站10000G+会员资源,会员资料板块,购买链接:点击进入购买VIP会员

JAVA高级面试进阶训练营视频教程

Java架构师系统进阶VIP课程

分布式高可用全栈开发微服务教程Go语言视频零基础入门到精通Java架构师3期(课件+源码)
Java开发全终端实战租房项目视频教程SpringBoot2.X入门到高级使用教程大数据培训第六期全套视频教程深度学习(CNN RNN GAN)算法原理Java亿级流量电商系统视频教程
互联网架构师视频教程年薪50万Spark2.0从入门到精通年薪50万!人工智能学习路线教程年薪50万大数据入门到精通学习路线年薪50万机器学习入门到精通教程
仿小米商城类app和小程序视频教程深度学习数据分析基础到实战最新黑马javaEE2.1就业课程从 0到JVM实战高手教程MySQL入门到精通教程
查看: 736|回复: 0

[Asp.net MVC]HandleErrorAttribute异常过滤器

[复制链接]
  • TA的每日心情
    奋斗
    2024-11-24 15:47
  • 签到天数: 804 天

    [LV.10]以坛为家III

    2053

    主题

    2111

    帖子

    72万

    积分

    管理员

    Rank: 9Rank: 9Rank: 9

    积分
    726782
    发表于 2021-4-20 10:14:47 | 显示全部楼层 |阅读模式

    摘要

    在asp.net mvc中除了使用try...catch/finally来处理异常外,它提供了一种通过在Controller或者Action上添加特性的方式来处理异常。

    HandleErrorAttribute

    首先看一下该特性的定义

    using System;
    
    namespace System.Web.Mvc
    {
        // 摘要: 
        //     表示一个特性,该特性用于处理由操作方法引发的异常。
        [AttributeUsage(AttributeTargets.Class | AttributeTargets.Method, Inherited = true, AllowMultiple = true)]
        public class HandleErrorAttribute : FilterAttribute, IExceptionFilter
        {
            // 摘要: 
            //     初始化 System.Web.Mvc.HandleErrorAttribute 类的新实例。
            public HandleErrorAttribute();
    
            // 摘要: 
            //     获取或设置异常的类型。
            //
            // 返回结果: 
            //     异常的类型。
            public Type ExceptionType { get; set; }
            //
            // 摘要: 
            //     获取或设置用于显示异常信息的母版视图。
            //
            // 返回结果: 
            //     母版视图。
            public string Master { get; set; }
            //
            // 摘要: 
            //     获取此特性的唯一标识符。
            //
            // 返回结果: 
            //     此特性的唯一标识符。
            public override object TypeId { get; }
            //
            // 摘要: 
            //     获取或设置用于显示异常信息的页视图。
            //
            // 返回结果: 
            //     页视图。
            public string View { get; set; }
    
            // 摘要: 
            //     在发生异常时调用。
            //
            // 参数: 
            //   filterContext:
            //     操作筛选器上下文。
            //
            // 异常: 
            //   System.ArgumentNullException:
            //     filterContext 参数为 null。
            public virtual void OnException(ExceptionContext filterContext);
        }
    }

    ExceptionType:属性,相当于try catch(Exception)中的catch捕获的异常类型,默认所有异常类型。

    View:异常展示视图,这个视图需要在目录Views/Shared/下。例如:

    Order:该属性是父类FilterAttribute的一个属性,用来获取或者设置执行操作筛选器的顺序,默认-1,-1最先执行。

    一个例子

    在Index中直接抛出一个异常,我们现在需要做的就是通过HandlerError特性捕获到这个异常,并且在视图MyError上显示详细信息。

    步骤1:添加特性

        public class UserController : Controller
        {
            // GET: User
            [HandleError(ExceptionType = typeof(Exception), View = "MyError")]
            public ActionResult Index()
            {
                throw new Exception("Sorry,threre is an error in your web server.");
            }
    
        }

    步骤2:定义错误视图,并通过@Model获取异常对象并显示错误信息。

    @{
        Layout = null;
    }
    
    <!DOCTYPE html>
    
    <html>
    <head>
        <meta name="viewport" content="width=device-width" />
        <title></title>
    </head>
    <body>
        <div>
            @Model.Exception.GetType().Name<br />
            @Model.Exception.Message<br />
            @Model.ControllerName<br />
            @Model.ActionName<br />
            @Model.Exception.StackTrace<br />
        </div>
    </body>
    </html>

    步骤3:注册过滤器。

    在App_Start目录添加类FilterConfig

        public class FilterConfig
        {
            public static void RegisterGlobalFilters(GlobalFilterCollection filters)
            {
                filters.Add(new HandleErrorAttribute());
            }
        }

    在Global.asax中注册

        public class MvcApplication : System.Web.HttpApplication
        {
            protected void Application_Start()
            {
                AreaRegistration.RegisterAllAreas();
                FilterConfig.RegisterGlobalFilters(GlobalFilters.Filters);
                RouteConfig.RegisterRoutes(RouteTable.Routes);
                GlobalConfiguration.Configure(WebApiConfig.Register);
    
            }
        }

    步骤4:开启自定义错误配置

      <system.web>
        ...
        <customErrors mode="On"></customErrors>
      </system.web>

    测试

    以上是采用ErrorHanlder的默认实现的方式,当然我们也可以自定义异常处理过滤器,方法很简单继承HandleErrorAttribute类,并且重写OnException方法即可。

        /// <summary>
        /// 自定义异常过滤器
        /// </summary>
        public class CustomerErrorAttribute : HandleErrorAttribute
        {
            public override void OnException(ExceptionContext filterContext)
            {
                //如果没有处理该异常
                if (!filterContext.ExceptionHandled)
                {
                    if (filterContext.Exception.Message.Contains("Sorry,threre is an error in your web server."))
                    {
                        filterContext.ExceptionHandled = true;
                        filterContext.HttpContext.Response.Write("这是一个自定义异常处理过滤器");
                    }
                }
            }
        }
        public class UserController : Controller
        {
            // GET: User
            [CustomerError(ExceptionType = typeof(Exception), View = "MyError")]
            public ActionResult Index()
            {
                throw new Exception("Sorry,threre is an error in your web server.");
            }
    
        }
        public class FilterConfig
        {
            public static void RegisterGlobalFilters(GlobalFilterCollection filters)
            {
                filters.Add(new HandleErrorAttribute());
                filters.Add(new CustomerErrorAttribute());
            }
        }

    测试

    好了,自定义的异常处理过滤器已经起作用了。

    需要注意在自定义处理异常过滤器的时候需要重写OnException方法,该方法有一个ExceptionContext类型的参数。

        // 摘要: 
        //     提供使用 System.Web.Mvc.HandleErrorAttribute 类的上下文。
        public class ExceptionContext : ControllerContext
        {
            // 摘要: 
            //     初始化 System.Web.Mvc.ExceptionContext 类的新实例。
            public ExceptionContext();
            //
            // 摘要: 
            //     使用指定的控制器上下文针对指定的异常初始化 System.Web.Mvc.ExceptionContext 类的新实例。
            //
            // 参数: 
            //   controllerContext:
            //     控制器上下文。
            //
            //   exception:
            //     异常。
            //
            // 异常: 
            //   System.ArgumentNullException:
            //     exception 参数为 null。
            public ExceptionContext(ControllerContext controllerContext, Exception exception);
    
            // 摘要: 
            //     获取或设置异常对象。
            //
            // 返回结果: 
            //     异常对象。
            public virtual Exception Exception { get; set; }
            //
            // 摘要: 
            //     获取或设置一个值,该值指示是否已处理异常。
            //
            // 返回结果: 
            //     如果已处理异常,则为 true;否则为 false。
            public bool ExceptionHandled { get; set; }
            //
            // 摘要: 
            //     获取或设置操作结果。
            //
            // 返回结果: 
            //     操作结果。
            public ActionResult Result { get; set; }
        }

    需要注意的是,在自定义的异常过滤器中,如果对异常已经处理了,需要将ExceptionHandled设置为true,这样其它的过滤器可以根据该值判断当前异常是否已经处理过了。

    通过异常处理过滤器的特性,你可以更方便的来处理action或者Controller中的异常,比try--catch用起来更方便,用这种方式,也可以简化异常处理的代码,少一些大块儿大块儿的异常处理代码。

    哎...今天够累的,签到来了1...
    回复

    使用道具 举报

    您需要登录后才可以回帖 登录 | 立即注册

    本版积分规则

    QQ|手机版|小黑屋|Java自学者论坛 ( 声明:本站文章及资料整理自互联网,用于Java自学者交流学习使用,对资料版权不负任何法律责任,若有侵权请及时联系客服屏蔽删除 )

    GMT+8, 2024-12-22 16:23 , Processed in 0.054132 second(s), 28 queries .

    Powered by Discuz! X3.4

    Copyright © 2001-2021, Tencent Cloud.

    快速回复 返回顶部 返回列表