0

I'm working on creating custom error pages in my ASP.NET MVC 4 web application. I've already implemented OnException error handling and controller decorating with attributes, but I wanted to have custom error pages for URLs that didn't fall under any controller routes so I resorted to the Global.asax's Application_Error.

Following @Darin's (thanks btw!) response in this question here, I have everything setup accordingly but I get an issue when the controller renders the view on the client side. When it returns a view, it returns all of the HTML rendered inside of a<pre> tag. I'm using Chrome's dev tools when I see this. This happens in Chrome, Safari, and Mozilla (maybe more, I didn't bother to check after those). Oddly, the views render fine in IE though. I've googled around and looked around other questions and haven't found much on this. Would anyone happen to know how/why this happens, and a workaround fix for it? As a last ditch effort, I thought about getting the View as a string and using return Content(...) instead, but it seems a little much for what it's worth.

tl;dr - If I could have some input on why my view HTML is being rendered inside of a <pre> tag, that would be awesome! I'm sure it's browser-rendering specific, but I'm not going to settle on this only works in IE.

Controller:

public class ErrorsController : Controller
{      

    public ActionResult PageNotFound()
    {
        Response.StatusCode = 404;

        var vm = new ErrorViewModel()
        {
            ErrorMessage = "The page you requested could not be found.",
            StatusCode = Response.StatusCode
        };

        Response.TrySkipIisCustomErrors = true;            
        return View("PageNotFound", vm);
    }

View:

@{
Layout = "~/Views/Shared/_GenericLayout.cshtml";
}

<h1 class="error">Oh No!</h1>

@if(Model.ErrorMessage != null && Model.StatusCode != null)
{
    <h2><em>@Model.StatusCode</em> - @Model.ErrorMessage</h2>
}
else
{
    <h2>The page you requested could not be found.</h2>    
}

Global.asax:

 protected void Application_Error(object sender, EventArgs e)
    {
        if (Context.IsCustomErrorEnabled)
        {
            ShowCustomErrorPage(Server.GetLastError());
        }
    }

    private void ShowCustomErrorPage(Exception exception)
    {
        HttpException httpException = exception as HttpException;

        Response.Clear();

        RouteData routeData = new RouteData();
        routeData.Values.Add("controller", "Errors");
        routeData.Values.Add("fromAppErrorEvent", true);

        if (httpException != null)
        {
            Response.StatusCode = httpException.GetHttpCode();
            switch(Response.StatusCode)
            {
                case 404:
                    routeData.Values.Add("action", "PageNotFound");
                    break;
                case 403:
                    routeData.Values.Add("action", "PageForbidden");
                    break;
            }
        }

        Server.ClearError();

        IController controller = new ErrorsController();
        RequestContext rc = new RequestContext(new HttpContextWrapper(Context), routeData);
        controller.Execute(rc);
    }

1 Answer 1

3

Simple fix. Chrome wasn't recognizing what it was receiving, so explicitly defining the response's content type to "text/html" before returning the view fixed the problem.

public ActionResult PageNotFound()
{
    Response.StatusCode = 404;

    var vm = new ErrorViewModel()
    {
        ErrorMessage = "The page you requested could not be found.",
        StatusCode = Response.StatusCode
    };

    Response.ContentType = "text/html";
    Response.TrySkipIisCustomErrors = true;            
    return View("PageNotFound", vm);
}
Sign up to request clarification or add additional context in comments.

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.