以下のコードでは、ユーザーがメッセージを入力して"Send"ボタンを押すと、そのメッセージがサーバーにPOSTリクエストとして送信されます。そして、2秒ごとにGETリクエストを送信してチャットボックスを更新します。
ただし、このサンプルコードはかなり簡易的で、本番環境での使用を前提としたものではありません。本番環境では、より高度な技術(WebSocketなど)やフレームワーク(Spring、Node.jsなど)を使用することを強く推奨します。
<!DOCTYPE html>
<html>
<head>
<meta charset="UTF-8">
<title>Chat App</title>
<script
src="https://ajax.googleapis.com/ajax/libs/jquery/3.5.1/jquery.min.js"></script>
<script>
// jQueryライブラリを使用します。このスクリプトタグはHTMLページに埋め込むためのものです。
$(document).ready(function() {
// ドキュメント(ページ)が読み込まれ、準備ができたら以下のコードを実行します。
$("#sendMessage").click(function() {
// IDが"sendMessage"のHTML要素(ボタンなど)がクリックされたときに、以下のコードを実行します。
let message = $("#message").val();
// IDが"message"のHTML要素(テキストフィールドなど)から値を取得し、それを変数"message"に代入します。
$.post("Chat", {
message : message
});
// "Chat"というエンドポイントに対してPOSTリクエストを送信します。このリクエストのボディには、先ほど取得した"message"の値が含まれます。
$("#message").val("");
// メッセージを送信した後、IDが"message"のHTML要素の値を空にします(テキストフィールドをクリアします)。
});
setInterval(function() {
// 指定した時間間隔(この場合は2000ミリ秒、つまり2秒)ごとに、以下のコードを実行します。
$.get("Chat", function(data, status) {
// "Chat"というエンドポイントからGETリクエストを送信し、レスポンスが返ってきたら以下のコードを実行します。
// "data"はサーバーから返されたデータ、"status"はリクエストのステータス("success"、"notmodified"など)です。
$("#chatBox").html(data);
// IDが"chatBox"のHTML要素(テキストエリアなど)の内容を、サーバーから返されたデータ("data")で更新します。
});
}, 2000);
// setIntervalの第2引数は、指定したコードを実行する時間間隔(ミリ秒)です。この場合は2000ミリ秒、つまり2秒です。
});
</script>
</head>
<body>
<textarea id="chatBox" readonly rows="10" cols="30"></textarea>
<br />
<input type="text" id="message">
<button id="sendMessage">Send</button>
</body>
</html>
package controller;
import java.io.IOException;
import java.io.PrintWriter;
import java.util.Queue;
import java.util.concurrent.ConcurrentLinkedQueue;
import javax.servlet.ServletException;
import javax.servlet.annotation.WebServlet;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
@WebServlet("/Chat")
public class ChatServlet extends HttpServlet {
private static final Queue<String> messages = new ConcurrentLinkedQueue<>();
// スレッドセーフなQueueインスタンスを作成します。このQueueは文字列のメッセージを保持します。静的(static)であり、すべてのChatServletインスタンス間で共有されます。
@Override
protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
// HTTP
// GETリクエストを処理するためのメソッドをオーバーライド(再定義)します。HttpServletRequestオブジェクトはリクエスト情報を、HttpServletResponseオブジェクトはレスポンス情報を保持します。
resp.setContentType("text/html");
// HTTPレスポンスのContent-Typeヘッダを"text/html"に設定します。これにより、レスポンスボディがHTMLであることをブラウザに伝えます。
PrintWriter out = resp.getWriter();
// HttpServletResponseオブジェクトからPrintWriterを取得します。これにより、レスポンスボディにテキストを書き込むことができます。
messages.forEach(out::println);
// "messages"
// Queueの各メッセージを、PrintWriterのprintlnメソッドを使ってレスポンスボディに書き込みます。つまり、保存されているすべてのメッセージをクライアントに送り返します。
}
@Override
protected void doPost(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
// HTTP POSTリクエストを処理するためのメソッドをオーバーライド(再定義)します。
String message = req.getParameter("message");
// HttpServletRequestオブジェクトから"message"という名前のパラメータを取得します。このパラメータは、クライアントから送信されたメッセージを含んでいます。
messages.add(message);
// 取得したメッセージを"messages" Queueに追加します。
}
}
なお、このサンプルコードではエラーハンドリングやセキュリティ対策などは考慮していません。実際のアプリケーションで使用する場合は、それらの重要な要素も適切に考慮する必要があります。