How do I show Exception message in shared view Error.cshtml?

10,739

Override the filter:

// In your App_Start folder
public class FilterConfig
{
    public static void RegisterGlobalFilters(GlobalFilterCollection filters)
    {
        filters.Add(new ErrorFilter());
        filters.Add(new HandleErrorAttribute());
        filters.Add(new SessionFilter());
    }
}

// In your filters folder (create this)
public class ErrorFilter : System.Web.Mvc.HandleErrorAttribute
{
    public override void OnException(System.Web.Mvc.ExceptionContext filterContext)
    {
        System.Exception exception = filterContext.Exception;
        string controller = filterContext.RouteData.Values["controller"].ToString();;
        string action = filterContext.RouteData.Values["action"].ToString();

        if (filterContext.ExceptionHandled)
        {
            return;
        }
        else
        {
            // Determine the return type of the action
            string actionName = filterContext.RouteData.Values["action"].ToString();
            Type controllerType = filterContext.Controller.GetType();
            var method = controllerType.GetMethod(actionName);
            var returnType = method.ReturnType;

            // If the action that generated the exception returns JSON
            if (returnType.Equals(typeof(JsonResult)))
            {
                filterContext.Result = new JsonResult()
                {
                    Data = "DATA not returned"
                };
            }

            // If the action that generated the exception returns a view
            if (returnType.Equals(typeof(ActionResult))
                || (returnType).IsSubclassOf(typeof(ActionResult)))
            {
                filterContext.Result = new ViewResult
                {
                    ViewName = "Error"
                };
            }
        }

        // Make sure that we mark the exception as handled
        filterContext.ExceptionHandled = true;
    }
}

Declare the model at the top of the 'error' view:

@model System.Web.Mvc.HandleErrorInfo

Then use on the page like so:

@if (Model != null)
{
    <div>
        @Model.Exception.Message
        <br />
        @Model.ControllerName
    </div>
}

Hope this helps.

Share:
10,739
barrypicker
Author by

barrypicker

Technologist with a passion for live music, and things that burn gasoline to go fast.

Updated on June 12, 2022

Comments

  • barrypicker
    barrypicker almost 2 years

    If I start with a new MVC 5 project, in web.config setting customErrors mode="on" allows the shared view 'Error.cshtml' to show when I force (raise) an exception, but it only shows the following text...

    Error.

    An error occurred while processing your request.

    How do I pass information to this view to display more relevant info, such as what error occurred? Can I use this view if I use the Global.asax method...

    protected void Application_Error()
    

    ?

  • barrypicker
    barrypicker almost 9 years
    Thanks Denys - your solution works well. I thinned out the code a bit to fit my particular need, but your example works right out of the box...
  • Avrohom Yisroel
    Avrohom Yisroel about 6 years
    Couldn't get this to work. It couldn't resolve SessionFilter and even if I removed that line, the Model was always null in Error.cshtml. I copied your code verbatim. Any idea what went wrong? I'm using MVC5 if it makes any difference.
  • Denys
    Denys about 6 years
    Ignore SessionFilter - this is another filter you may create. Step through the filter to make sure it invokes your 'error' view. The view must be created shared and the name should be 'error' (match the viewname when setting new view result).
  • Triynko
    Triynko about 4 years
    The variables exception, controller, and action aren't even referenced. What's their purpose in this code?