Application_Error in global.asax not catching errors in WebAPI

后端 未结 2 1889
暖寄归人
暖寄归人 2020-12-01 10:20

For a project I am working on, one of the things we\'re implementing is something that we have code for in some of my teams older ASP.NET and MVC projects - an Applica

相关标签:
2条回答
  • 2020-12-01 10:44

    Abstract out your error handling logic from Application_Error into its own function. Create a Web API exception filter.

    //register your filter with Web API pipeline
    //this belongs in the Application_Start event in Global Application Handler class (global.asax)
    //or some other location that runs on startup
    GlobalConfiguration.Configuration.Filters.Add(new LogExceptionFilterAttribute());
    
    //Create filter
    public class LogExceptionFilterAttribute : ExceptionFilterAttribute 
    {
        public override void OnException(HttpActionExecutedContext context)
        {
            ErrorLogService.LogError(context.Exception);
        }
    }
    
    //in global.asax or global.asax.cs
    protected void Application_Error(object sender, EventArgs e)
    {
        Exception ex = Server.GetLastError();
        ErrorLogService.LogError(ex);
    } 
    
    //common service to be used for logging errors
    public static class ErrorLogService
    {
        public static void LogError(Exception ex)
        {
            //Email developers, call fire department, log to database etc.
        }
    }
    

    Errors from Web API do not trigger the Application_Error event. But we can create an exception filter and register it to handle the errors. Also see Global Error Handling in ASP.NET Web API 2.

    0 讨论(0)
  • 2020-12-01 10:54

    In my case, i prefer not use Web.config. Then i created code above in Global.asax file:

    protected void Application_Error(object sender, EventArgs e)
        {
            Exception ex = Server.GetLastError();
    
            //Not Found (When user digit unexisting url)
            if(ex is HttpException && ((HttpException)ex).GetHttpCode() == 404)
            {
                HttpContextWrapper contextWrapper = new HttpContextWrapper(this.Context);
    
                RouteData routeData = new RouteData();
                routeData.Values.Add("controller", "Error");
                routeData.Values.Add("action", "NotFound");
    
                IController controller = new ErrorController();
                RequestContext requestContext = new RequestContext(contextWrapper, routeData);
                controller.Execute(requestContext);
                Response.End();
            }
            else //Unhandled Errors from aplication
            {
                ErrorLogService.LogError(ex);
                HttpContextWrapper contextWrapper = new HttpContextWrapper(this.Context);
    
                RouteData routeData = new RouteData();
                routeData.Values.Add("controller", "Error");
                routeData.Values.Add("action", "Index");
    
                IController controller = new ErrorController();
                RequestContext requestContext = new RequestContext(contextWrapper, routeData);
                controller.Execute(requestContext);
                Response.End();
            }
        }
    

    And thtat is my ErrorController.cs

    public class ErrorController : Controller
    {
        // GET: Error
        public ViewResult Index()
        {
            Response.StatusCode = 500;
            Exception ex = Server.GetLastError();
            return View("~/Views/Shared/SAAS/Error.cshtml", ex);
        }
    
        public ViewResult NotFound()
        {
            Response.StatusCode = 404;
            return View("~/Views/Shared/SAAS/NotFound.cshtml");
        }
    }
    

    And that is my ErrorLogService.cs copyed from @mason class

    //common service to be used for logging errors
    public static class ErrorLogService
    {
        public static void LogError(Exception ex)
        {
            //Do what you want here, save log in database, send email to police station
        }
    }
    
    0 讨论(0)
提交回复
热议问题