有人与我立黄昏,有人问我粥可温。有人与我捻熄灯,有人共我书半生。——2019/1/22
延续上一篇MVC过滤器使用实例
异常过滤器,顾名思义,就是当程序发生异常时所使用的过滤器。用于在系统出现未捕获异常时的处理。
异常过滤器用于实现IExceptionFilter接口,并在ASP.NET MVC管道执行期间引发了未处理的异常时执行。异常过滤器可用于执行诸如日志记录或显示错误页之类的任务。自定义异常筛选器继承自HandleErrorAttribute
代码很简单:在App_Start里新建一个自定义异常处理类,继承HandleErrorAttribute,并重写OnException。
另外需要新建一个文件夹,用来存储日志文件。下面代码会体现到
public class ErrorAttribute: HandleErrorAttribute
{
/// <summary>
/// 在发生异常时触发调用
/// </summary>
public override void OnException(ExceptionContext filterContext)
{
//if (!filterContext.ExceptionHandled && filterContext.Exception is NullReferenceException)
if (!filterContext.ExceptionHandled)
{
//获取出现异常的controller名和action名,用于记录
string controllerName = (string)filterContext.RouteData.Values["controller"];
string actionName = (string)filterContext.RouteData.Values["action"];
//定义一个HandErrorInfo,用于Error视图展示异常信息
HandleErrorInfo model = new HandleErrorInfo(filterContext.Exception, controllerName, actionName);
string thisTime = DateTime.Now.ToShortDateString().Replace("/","");
string errorDetails = $"出错时间:{DateTime.Now.ToString()},错误发生在{model.ControllerName}控制器的{model.ActionName},错误类型:{model.Exception.Message}";
string splitLine = "——————————————————————分割线——————————————————————";
using (System.IO.StreamWriter file = new System.IO.StreamWriter(@"E:\ybbb\YbbFighting\YbbFighting\ErrorTxt\"+ thisTime, true))
{
file.WriteLine(errorDetails);
file.WriteLine(model.Exception.StackTrace);
file.WriteLine(splitLine);
}
ViewResult result = new ViewResult
{
ViewName = this.View,//设置异常时跳转的404页面
ViewData = new ViewDataDictionary<HandleErrorInfo>(model) //定义ViewData,泛型
};
filterContext.Result = result;
filterContext.ExceptionHandled = true;//设置异常已处理
}
}
}
注意下System.IO.StreamWriter,如果文件存在,设置为ture则向文件追加内容
在App_Start的FilterConfig里注册我们刚才写的自定义异常筛选器
新建一个Error页,就是我们注册时初始化的View,这里我发现即使不初始化View为Error,最后也会自己定向到Error页面,但是我把Error改名为Error1时,就会报错找不到Error页面,百度了下也没看到类似的情况,我也根本没在配置文件里配置这个。猜想可能是异常筛选器底层默认是Error吧。如果有大佬知道,麻烦告诉下。谢谢!
public ActionResult NewErrorDemo()
{
throw new Exception("我抛出了一个错误!");
return View();
}
运行程序:
日志信息如图: