加入收藏 | 设为首页 | 会员中心 | 我要投稿 李大同 (https://www.lidatong.com.cn/)- 科技、建站、经验、云计算、5G、大数据,站长网!
当前位置: 首页 > 编程开发 > asp.Net > 正文

asp.net-mvc – ASP.NET MVC应用程序自定义错误页面不显示在共享

发布时间:2020-12-15 22:58:20 所属栏目:asp.Net 来源:网络整理
导读:我在我的共享主机上部署的ASP.NET MVC应用程序出现了自定义错误的问题.我创建了一个ErrorController,并将以下代码添加到Global.asax以捕获未处理的异常,记录它们,然后将控件传输到ErrorController以显示自定义错误.此代码取自 here: protected void Applica
我在我的共享主机上部署的ASP.NET MVC应用程序出现了自定义错误的问题.我创建了一个ErrorController,并将以下代码添加到Global.asax以捕获未处理的异常,记录它们,然后将控件传输到ErrorController以显示自定义错误.此代码取自 here:
protected void Application_Error(object sender,EventArgs e)
{
    Exception ex = Server.GetLastError();
    Response.Clear();

    HttpException httpEx = ex as HttpException;
    RouteData routeData = new RouteData();
    routeData.Values.Add("controller","Error");

    if (httpEx == null)
    {
        routeData.Values.Add("action","Index");
    }
    else
    {
        switch (httpEx.GetHttpCode())
        {
            case 404:
                routeData.Values.Add("action","HttpError404");
                break;
            case 500:
                routeData.Values.Add("action","HttpError500");
                break;
            case 503:
                routeData.Values.Add("action","HttpError503");
                break;
            default:
                routeData.Values.Add("action","Index");
                break;
        }
    }

    ExceptionLogger.LogException(ex); // <- This is working. Errors get logged

    routeData.Values.Add("error",ex);
    Server.ClearError();
    IController controller = new ErrorController();
    // The next line doesn't seem to be working
    controller.Execute(new RequestContext(new HttpContextWrapper(Context),routeData));
}

Application_Error肯定是发射,因为日志记录工作正常,但是不是显示我的自定义错误页面,我得到了Go Daddy通用的.从博客标题的上述代码取自,我注意到它使用了MVC框架的Release Candidate 2.在1.0中有什么改变,使最后一行代码不起作用?像往常一样works great on my machine.

任何建议将不胜感激.

编辑:忘了提到我已经尝试过Web.config中的customErrors模式的所有3个可能性(Off,On和RemoteOnly).与此设置相同的结果.

编辑2:我也尝试过和没有[HandleError]装饰的Controller类.

更新:我已经弄清楚了404s. Go Daddy的主机控制中心中有一部分“设置”面板,其中可以控制404行为,默认情况是显示其通用页面,显然这将覆盖任何Web.config设置.所以我的自定义404页面现在按照预期显示.然而,五百和五十三秒仍然没有工作.如果Sql Server抛出异常,则HomeController中的代码将获取内容的静态文本版本,如下所示:

public ActionResult Index()
{
    CcmDataClassesDataContext dc = new CcmDataClassesDataContext();

    // This might generate an exception which will be handled in the OnException override
    HomeContent hc = dc.HomeContents.GetCurrentContent();

    ViewData["bodyId"] = "home";
    return View(hc);
}

protected override void OnException(ExceptionContext filterContext)
{
    // Only concerned here with SqlExceptions so an HTTP 503 message can
    // be displayed in the Home View. All others will bubble up to the
    // Global.asax.cs and be handled/logged there.
    System.Data.SqlClient.SqlException sqlEx =
        filterContext.Exception as System.Data.SqlClient.SqlException;
    if (sqlEx != null)
    {
        try
        {
            ExceptionLogger.LogException(sqlEx);
        }
        catch
        {
            // couldn't log exception,continue without crashing
        }

        ViewData["bodyId"] = "home";
        filterContext.ExceptionHandled = true;
        HomeContent hc = ContentHelper.GetStaticContent();
        if (hc == null)
        {
            // Couldn't get static content. Display friendly message on Home View.
            Response.StatusCode = 503;
            this.View("ContentError").ExecuteResult(this.ControllerContext);
        }
        else
        {
            // Pass the static content to the regular Home View
            this.View("Index",hc).ExecuteResult(this.ControllerContext);
        }
    }
}

以下是尝试获取静态内容的代码:

public static HomeContent GetStaticContent()
{
    HomeContent hc;

    try
    {
        string path = Configuration.CcmConfigSection.Config.Content.PathToStaticContent;
        string fileText = File.ReadAllText(path);
        string regex = @"^[^#]([^rn]*)";
        MatchCollection matches = Regex.Matches(fileText,regex,RegexOptions.Multiline);
        hc = new HomeContent
            {
                ID = Convert.ToInt32(matches[0].Value),Title = matches[1].Value,DateAdded = DateTime.Parse(matches[2].Value),Body = matches[3].Value,IsCurrent = true
            };
    }
    catch (Exception ex)
    {
        try
        {
            ExceptionLogger.LogException(ex);
        }
        catch
        {
            // couldn't log exception,continue without crashing
        }
        hc = null;
    }

    return hc;
}

我已经验证,如果我更改连接字符串以生成SqlException,代码正确记录错误,然后抓取并显示静态内容.但是如果我也改变Web.config中静态文本文件的路径来测试503版本的Home View,那么我所得到的只是一个没有“服务不可用”的页面.而已.没有定制的503消息与网站的外观和感觉.

有没有人有任何建议改进代码可能有帮助?是否有助于向HttpResponse添加不同的头文件?还是去爸爸狠狠劫持503s?

解决方法

我找到了解决方案,它非常简单.原来问题其实是在IIS7中.在Visual Studio中调试此问题时,我看到了以前没有注意到的HttpResponse对象的属性:
public bool TrySkipIisCustomErrors { get; set; }

这导致我到最近的搜索引擎,这个搜索引擎在angrypets.com和this question here on SO上发现了一个great blog post by Rick Strahl,而这些链接比我可以更好地解释了血腥细节,但是这个Rick的帖子引用得很好:

The real confusion here occurs because the error is trapped by
ASP.NET,but then ultimately still handled by IIS which looks at the
500 status code and returns the stock IIS error page.

在集成模式下,这种行为似乎也是IIS7特有的.从msdn:

When running in Classic mode in IIS 7.0 the TrySkipIisCustomErrors
property default value is true. When running in Integrated mode,the
TrySkipIisCustomErrors property default value is false.

所以基本上我最终都要做的是添加Response.TrySkipIisCustomErrors = true;在将Response.StatusCode设置为500或503的任何代码之后,所有内容都将按照设计进行功能.

(编辑:李大同)

【声明】本站内容均来自网络,其相关言论仅代表作者个人观点,不代表本站立场。若无意侵犯到您的权利,请及时与联系站长删除相关内容!

    推荐文章
      热点阅读