114

アプリケーション用にカスタム エラー ページを設定しました。

<customErrors mode="On" defaultRedirect="~/errors/GeneralError.aspx"
/>

Global.asax の Application_Error() では、次のコードが機能して例外の詳細を取得します。

  Exception ex = Server.GetLastError();
  if (ex != null)
    {
        if (ex.GetBaseException() != null)
            ex = ex.GetBaseException();
    }

エラー ページ (~/errors/GeneralError.aspx.cs) に到達するまでに、Server.GetLastError() は null です

Global.asax.cs ではなく、エラー ページで例外の詳細を取得する方法はありますか?

Vista/IIS7 上の ASP.NET 3.5

4

10 に答える 10

137

私の web.config 設定を詳しく見てみると、この投稿のコメントの 1 つが非常に役に立ちます。

asp.net 3.5 sp1 には新しいパラメータ redirectMode があります

したがってcustomErrors、このパラメーターを追加するように修正できます。

<customErrors mode="RemoteOnly" defaultRedirect="~/errors/GeneralError.aspx" redirectMode="ResponseRewrite" />

このResponseRewriteモードでは、ブラウザーをリダイレクトせずに «エラー ページ» を読み込むことができるため、URL は同じままであり、私にとって重要なことに、例外情報が失われることはありません。

于 2008-12-05T06:33:14.157 に答える
38

OK、次の投稿を見つけました: http://msdn.microsoft.com/en-us/library/aa479319.aspx

この非常にわかりやすい図で:

ダイアグラム
(ソース: microsoft.com )

本質的に、これらの例外の詳細を取得するには、カスタム エラー ページで後で取得できるように、それらを Global.asax に保存する必要があります。

ロジックではなく役立つコンテンツを処理するカスタム エラー ページを使用して、Global.asax で大部分の作業を行うのが最善の方法のようです。

于 2008-12-05T06:23:32.850 に答える
18

NailItDown と Victor の発言を組み合わせたものです。推奨/最も簡単な方法は、Global.Asax を使用してエラーを保存し、カスタム エラー ページにリダイレクトすることです。

Global.asax :

    void Application_Error(object sender, EventArgs e) 
{
    // Code that runs when an unhandled error occurs
    Exception ex = Server.GetLastError();
    Application["TheException"] = ex; //store the error for later
    Server.ClearError(); //clear the error so we can continue onwards
    Response.Redirect("~/myErrorPage.aspx"); //direct user to error page
}

さらに、 web.configを設定する必要があります。

  <system.web>
    <customErrors mode="RemoteOnly" defaultRedirect="~/myErrorPage.aspx">
    </customErrors>
  </system.web>

最後に、エラー ページに保存した例外を使用して、必要なことをすべて実行します。

protected void Page_Load(object sender, EventArgs e)
{

    // ... do stuff ...
    //we caught an exception in our Global.asax, do stuff with it.
    Exception caughtException = (Exception)Application["TheException"];
    //... do stuff ...
}
于 2008-12-05T19:29:30.610 に答える
6

global.asax.csServer.Transfer("~/ErrorPage.aspx");のメソッド内からのようなものを使用してみてくださいApplication_Error()

次にPage_Load()、ErrorPage.aspx.cs 内から、次のようなことを行っても問題ありません。Exception exception = Server.GetLastError().GetBaseException();

Server.Transfer()例外がぶら下がっているようです。

于 2009-04-23T04:27:36.150 に答える
5

ここにはいくつかの良い答えがありますが、システム例外メッセージをエラーページに表示するのは良い習慣ではないことを指摘しなければなりません(これはあなたがやりたいと思っていることです)。悪意のあるユーザーに、望まないことをうっかり明らかにしてしまう可能性があります。たとえば、SQL Serverの例外メッセージは非常に冗長であり、エラーが発生したときにデータベースのユーザー名、パスワード、およびスキーマ情報を提供できます。その情報はエンドユーザーに表示されるべきではありません。

于 2011-06-07T20:39:08.660 に答える
5

これが私の解決策です..

Global.aspx:

void Application_Error(object sender, EventArgs e)
    {
        // Code that runs when an unhandled error occurs

        //direct user to error page 
        Server.Transfer("~/ErrorPages/Oops.aspx"); 
    }

Oops.aspx で:

protected void Page_Load(object sender, EventArgs e)
    {
        if (!IsPostBack)
            LoadError(Server.GetLastError()); 
    }

    protected void LoadError(Exception objError)
    {
        if (objError != null)
        {
            StringBuilder lasterror = new StringBuilder();

            if (objError.Message != null)
            {
                lasterror.AppendLine("Message:");
                lasterror.AppendLine(objError.Message);
                lasterror.AppendLine();
            }

            if (objError.InnerException != null)
            {
                lasterror.AppendLine("InnerException:");
                lasterror.AppendLine(objError.InnerException.ToString());
                lasterror.AppendLine();
            }

            if (objError.Source != null)
            {
                lasterror.AppendLine("Source:");
                lasterror.AppendLine(objError.Source);
                lasterror.AppendLine();
            }

            if (objError.StackTrace != null)
            {
                lasterror.AppendLine("StackTrace:");
                lasterror.AppendLine(objError.StackTrace);
                lasterror.AppendLine();
            }

            ViewState.Add("LastError", lasterror.ToString());
        }
    }

   protected void btnReportError_Click(object sender, EventArgs e)
    {
        SendEmail();
    }

    public void SendEmail()
    {
        try
        {
            MailMessage msg = new MailMessage("webteam", "webteam");
            StringBuilder body = new StringBuilder();

            body.AppendLine("An unexcepted error has occurred.");
            body.AppendLine();

            body.AppendLine(ViewState["LastError"].ToString());

            msg.Subject = "Error";
            msg.Body = body.ToString();
            msg.IsBodyHtml = false;

            SmtpClient smtp = new SmtpClient("exchangeserver");
            smtp.Send(msg);
        }

        catch (Exception ex)
        {
            lblException.Text = ex.Message;
        }
    }
于 2011-09-28T16:03:16.633 に答える
4

ここで誰もが見逃している重要な考慮事項の 1 つは、負荷分散 (Web ファーム) のシナリオです。global.asax を実行しているサーバーは、カスタム エラー ページの実行に関するサーバーとは異なる可能性があるため、Application に例外オブジェクトを格納することは信頼できません。

Webファーム構成でこの問題に対する信頼できる解決策、および/またはカスタムエラーページでServer.GetLastErrorで例外を拾うことができない理由についてのMSからの適切な説明を探しています。 global.asax Application_Error で。

PS 最初にロックしてからロック解除せずに Application コレクションにデータを保存するのは安全ではありません。

于 2010-06-05T20:23:01.563 に答える
2

これは、以下の 2 つのトピックに関連しています。GetHtmlErrorMessage と Session on Error ページの両方を取得したいと考えています。

ResponseRewrite 後にセッションが null になる

redirectMode = ResponseRewrite のときに HttpContext.Session が null になるのはなぜですか

私は必要のない解決策を試してみましたServer.Transfer() or Response.Redirect()

最初: web.config で ResponseRewrite を削除します

Web.config

<customErrors defaultRedirect="errorHandler.aspx" mode="On" />

次に Global.asax

    void Application_Error(object sender, EventArgs e)
    {
         if(Context.IsCustomErrorEnabled)
         {     
            Exception ex = Server.GetLastError();
            Application["TheException"] = ex; //store the error for later
         }
    }

次に、errorHandler.aspx.cs

        protected void Page_Load(object sender, EventArgs e)
            {       
                string htmlErrorMessage = string.Empty ;
                Exception ex = (Exception)Application["TheException"];
                string yourSessionValue = HttpContext.Current.Session["YourSessionId"].ToString();

                //continue with ex to get htmlErrorMessage 
                if(ex.GetHtmlErrorMessage() != null){              
                    htmlErrorMessage = ex.GetHtmlErrorMessage();
                }   
                // continue your code
            }

参考までに

http://www.developer.com/net/asp/article.php/3299641/ServerTransfer-Vs-ResponseRedirect.htm

于 2016-12-15T13:06:01.190 に答える
1

ここにはいくつかのオプションがあると思います。

最後の例外をセッションに保存し、カスタム エラー ページから取得できます。または、Application_error イベント内でカスタム エラー ページにリダイレクトすることもできます。後者を選択した場合は、必ず Server.Transfer メソッドを使用する必要があります。

于 2008-12-05T19:05:15.417 に答える