方法 : 安全なエラー メッセージを表示する

更新 : 2007 年 11 月

アプリケーションがエラー メッセージを表示するときは、悪意のあるユーザーがシステムを攻撃するのに役立つ情報を出力しないようにする必要があります。たとえば、アプリケーションがデータベースへのログインに失敗した場合に、使用しているユーザー名を含んだエラー メッセージを表示することは避ける必要があります。

エラー メッセージを制御する方法を次に示します。

  • 詳細なエラー メッセージをリモート ユーザーに表示しないようにアプリケーションを設定します (リモート ユーザーとは、Web サーバー コンピュータで作業をしているときにページを要求しないユーザーを表します)。オプションで、エラーをアプリケーション ページにリダイレクトできます。

  • 実現可能な場合は常にエラー処理を含め、独自のエラー メッセージを作成します。エラー ハンドラ内で、ユーザーがローカルで相応に応答するかどうかをテストできます。

  • 処理できない例外をすべてキャッチしてそれを汎用エラー ページにルーティングする、グローバルなエラー ハンドラをページ レベルまたはアプリケーション レベルで作成します。これにより、開発者が問題を予測できなかった場合でも、少なくとも例外ページはユーザーに表示されません。

リモート ユーザーにエラーを表示しないようにアプリケーションを設定するには

  • アプリケーションの Web.config ファイルで、customErrors 要素に次の変更を加えます。

    • mode 属性を RemoteOnly に設定します (大文字/小文字が区別されます)。これにより、アプリケーションは詳細なエラーをローカル ユーザー (つまり開発者) だけに表示します。

    • オプションで、アプリケーション エラー ページを指す defaultRedirect 属性を指定します。

    • オプションで、特定のエラーを特定のページにリダイレクトする <error> 要素を指定します。たとえば、標準 404 エラー (page not found) を自分のアプリケーションのページにリダイレクトできます。

    Web.config ファイルにおける一般的な customErrors ブロックのコード例を次に示します。

    <customErrors mode="RemoteOnly" defaultRedirect="AppErrors.aspx"> 
       <error statusCode="404" redirect="NoSuchPage.aspx"/> 
       <error statusCode="403" redirect="NoAccessAllowed.aspx"/> 
    </customErrors> 
    

エラー処理を含めるには

  1. エラーを生成する可能性のあるステートメントの周囲に try-catch ブロックを使用します。

  2. オプションで、IsLocal プロパティを使用してローカル ユーザーをテストし、エラー処理を修正します。値 127.0.0.1 は localhost に相当し、ブラウザが Web サーバーと同じコンピュータ上にあることを表します。

    エラー処理ブロックのコード例を次に示します。エラーが発生すると、メッセージおよびアプリケーションの詳細が Session 状態変数に読み込まれます。次に、その Session 状態変数を読み取ってエラーを表示できるページが表示されます (攻略的ステートメントを含んだ詳細文をユーザーに渡さないように、意図的にエラーが書き込まれます)。ユーザーがローカルな場合、これとは異なるエラー詳細が出力されます。finally ブロックでは、開かれているリソースが解放されます。

    Try
       SqlConnection1.Open()
       SqlDataAdapter1.Fill(Me.DsPubs1)
    Catch ex As Exception
       If Request.IsLocal Then
          Session("CurrentError") = ex.Message
        Else
          Session("CurrentError") = "Error processing page."
        End If
        Server.Transfer("ApplicationError.aspx")
    Finally
           SqlConnection1.Close()
    End Try
    
    try
    {
        sqlConnection1.Open();
        sqlDataAdapter1.Fill(dsCustomers1);
    }
    catch (Exception ex)
    {
        if(Request.IsLocal)
        { Session["CurrentError"] = ex.Message; }
        else
        { Session["CurrentError"] = "Error processing page."; }
        Server.Transfer("ApplicationError.aspx");
    }
    finally 
    {
        this.sqlConnection1.Close();
    }
    

グローバル エラー ハンドラの作成

また、ページ レベルまたはアプリケーション全体で処理できない例外をすべてキャッチするエラー ハンドラを作成できます。

グローバル エラー ハンドラを作成するには

  • ページ内にグローバル エラー ハンドラを作成するには、TemplateControl.Error イベントのハンドラを作成します。アプリケーション全体にわたるエラー ハンドラを作成するには、Global.asax ファイル内で、HttpApplication.Error イベントにコードを追加します。これらのメソッドは、ページまたはアプリケーションそれぞれで処理できない例外が発生した場合に呼び出されます。最後に発生したエラーに関する情報は、GetLastError メソッドから入手できます。

    994a1482.alert_note(ja-jp,VS.90).gifメモ :

    グローバル エラー ハンドラは、customErrors 構成要素の defaultRedirect 属性に指定されているエラー処理よりも優先されます。

    次のコード例のハンドラは、現在のエラーに関する情報を取得してそれを Session 変数に格納した後、エラー情報を抽出して表示できる汎用のエラー処理ページを呼び出します。

    Sub Application_Error(ByVal sender As Object, ByVal e As EventArgs)
        Session("CurrentError") = "Global: " & _
            Server.GetLastError.Message
        Server.Transfer("lasterr.aspx")
    End Sub
    
    protected void Application_Error(Object sender, EventArgs e)
    {
        Session["CurrentError"] = "Global: " + 
            Server.GetLastError().Message;
        Server.Transfer("lasterr.aspx");
    }
    

参照

その他の技術情報

ASP.NET Web サイトのセキュリティ