Servlet デバッグ

テスト/デバッグ用の Servlet は、開発および使用の過程で常に難しいものです。Servlet は多くの場合、クライアント/サーバー間の大量のやり取りを伴うため、エラーが発生しても再現が困難な場合があります。

ここでは、デバッグに役立つヒントとアドバイスをいくつか紹介します。

System.out.println()

System.out.println() は、特定のコードが実行されたかどうかをテストするためのマーカーとして使用されます。変数の値も出力できます。さらに:

  • System オブジェクトはコア Java オブジェクトの一部であるため、追加のクラスをインストールしなくてもどこでも使用できます。これには、Servlet、JSP、RMI、EJB、通常の Beans やクラス、およびスタンドアロンアプリケーションが含まれます。
  • ブレークポイントで停止するのとは異なり、System.out への書き込みはアプリケーションの通常の実行フローを妨げないため、タイミングが重要である場合に特に価値があります。

以下は System.out.println() を使用する構文です:

System.out.println("Debugging message");

上記の構文で生成されたすべてのメッセージは、Web サーバーのログファイルに記録されます。

メッセージログ

適切なログ記録メソッドを使用して、すべてのデバッグ、警告、およびエラーメッセージを記録することは非常に良い考えであり、推奨されます。log4Jすべてのメッセージを記録するために。

Servlet API は、log() メソッドを使用して情報を出力する簡単な方法も提供します。以下に示すとおりです:

// 导入必需的 java 库
import java.io.*;
import javax.servlet.*;
import javax.servlet.http.*;

public class ContextLog extends HttpServlet {
  public void doGet(HttpServletRequest request, 
      HttpServletResponse response) throws ServletException,
         java.io.IOException {
    
      String par = request.getParameter("par1");
      // 调用两个 ServletContext.log 方法
      ServletContext context = getServletContext( );

      if (par == null || par.equals(""))
      // 通过 Throwable 参数记录版本
      context.log("No message received:",
          new IllegalStateException("Missing parameter"));
      else
          context.log("Here is the visitor's message: " + par);
      
      response.setContentType("text/html;charset=UTF-8");
      java.io.PrintWriter out = response.getWriter( );
      String title = "Context Log";
      String docType = "<!DOCTYPE html> \n";
      out.println(docType +
        "<html>\n" +
        "<head><title>" + title + "</title></head>\n" +
        "<body bgcolor=\"#F0F0F0\">\n" +
        "<h1 align=\"center\">" + title + "</h1>\n" +
        "<h2 align=\"center\">Messages sent</h2>\n" +
        "</body></html>");
    } //doGet
}

ServletContext は、そのテキストメッセージを Servlet コンテナのログファイルに記録します。Tomcat の場合、これらのログは <Tomcat-installation-directory>/logs ディレクトリにあります。

これらのログファイルは、新たに発生したエラーや問題の頻度に関する指標を実際に提供します。そのため、通常は発生しない例外の catch 句で log() 関数を使用することをお勧めします。

JDB デバッガを使用する

アプレットまたはアプリケーションをデバッグするための jdb コマンドを使用して、Servlet をデバッグできます。

Servlet をデバッグするには、sun.servlet.http.HttpServer をデバッグし、それを HttpServer がブラウザからの HTTP リクエストに応答して Servlet を実行するものとみなします。これはアプレットのデバッグと非常に似ています。アプレットのデバッグと異なる点は、実際にデバッグされるプログラムが sun.applet.AppletViewer であることです。

ほとんどのデバッガは、アプレットのデバッグ方法の詳細を自動的に隠します。同様に、servlet の場合、デバッガが以下の操作を実行できるようにする必要があります:

  • デバッガのクラスパス classpath を設定して、sun.servlet.http.Http-Server および関連クラスを見つけられるようにします。
  • デバッガのクラスパス classpath を設定して、servlet とサポートクラスを見つけられるようにします。これらは通常、server_root/servlets および server_root/classes にあります。

通常、server_root/servlets をクラスパスに含めたくないでしょう。servlet の再読み込みが無効になるためです。しかし、この包含ルールはデバッグには非常に役立ちます。これにより、デバッガは HttpServer 内のカスタム Servlet ローダーが Servlet をロードする前に、Servlet 内にブレークポイントを設定できます。

正しいクラスパス classpath を設定したら、sun.servlet.http.HttpServer のデバッグを開始できます。デバッグしたい Servlet コードにブレークポイントを設定し、Web ブラウザを使用して指定された Servlet(http://localhost:8080/servlet/ServletToDebug)で HttpServer にリクエストを送信します。プログラムがブレークポイントに達すると停止するのがわかります。

コメントを使用する

コード内のコメントは、さまざまな方法でデバッグに役立ちます。コメントは、デバッグプロセスの他の多くの方法でも使用できます。

この Servlet は、Java のコメントと単行コメント(//...)を使用しています。複数行コメント(/* ...*/)は、Java コードの一部を一時的に削除するために使用できます。バグが消えた場合は、コメントアウトしたコードを注意深く確認し、問題の原因を特定してください。

クライアントおよびサーバー側のヘッダー情報

時には、Servlet が期待どおりに動作しない場合、元の HTTP リクエストとレスポンスを確認することが非常に役立ちます。HTTP の構造に精通していれば、リクエストとレスポンスを読み、これらのヘッダー情報が実際に何であるかを確認できます。

重要なデバッグのヒント

以下に、Servlet デバッグのヒントをいくつか示します:

  • server_root/classes は再読み込みされませんが、server_root/servlets は再読み込みされる可能性があることに注意してください。
  • ブラウザに、表示中のページの元のコンテンツを表示するように要求します。これはフォーマットの問題を特定するのに役立ちます。通常は「表示」メニューのオプションです。
  • 完全な再読み込みを強制することで、ブラウザが前のリクエストの出力をキャッシュしていないことを確認します。Netscape Navigator では Shift-Reload を使用し、Internet Explorer では Shift-Refresh を使用してください。
  • servlet の init() メソッドが ServletConfig パラメータを受け取り、super.init(config) を呼び出すことを確認してください。
その他の拡張