Javaプログラミングでソケット通信を理解したいあなたに向けて、本記事では「サーバーとクライアントのやり取りはどう実現されているのか」「TCPプロトコルの特徴と役割」「3ウェイ・ハンドシェイクによる接続の確立」までを丁寧に解説します。
SocketとServerSocketの使い方を実際のコードで追体験しながら、ネットワークの基礎が自然と身につく構成になっています。
読み終える頃には、Javaでソケット通信を用いたシンプルなチャットアプリが自力で作れるレベルに到達するでしょう。
双方向通信のしくみを実装しながら、プログラムの流れや接続の裏側までしっかり把握したい方に最適な内容です。
ソケット通信とは?

ソケット通信とは、ネットワーク上の2つのプログラムが、ソケットと呼ばれる通信口を使ってやりとりする仕組みです。
具体的には、以下のような構成になります。
この2者が1対1でつながることで、データのやり取りができるようになります。
ソケットとは?
「ソケット」とは、通信を行うための“窓口”のようなものです。
送る側(クライアント)と受け取る側(サーバー)が、ソケットという窓口を通じてデータをやり取りします。
javaでは、クライアントはSocketクラスを使って接続し、サーバーはServerSocketクラスを使って接続を待ち受けます。
ソケット通信はどうやって実現してるの?
Javaのソケット通信は、裏側でTCP(Transmission Control Protocol)という通信プロトコルを使っています。
TCPは、以下のような特徴を持っています。
- データが順番通りに届く
- 途中でデータが欠けたり壊れたりしないよう保証する
- 通信の開始・終了を丁寧に行う(3ウェイ・ハンドシェイク)
つまり、「ちゃんと確実にデータを届けてくれる郵便屋さん」みたいなものです。
JavaでSocketやServerSocketを使った通信は、基本的にこのTCP通信の仕組みにのっとって動いています。
だから、ネットワークの知識があまりなくても、Javaのソケット通信を使えば自然と「正しく届く通信」が実現できるのです。
3ウェイ・ハンドシェイク
3ウェイ・ハンドシェイクについて詳しく見てきましょう。
手順1:クライアント → サーバーへ「SYN」(接続要求)
クライアントが「これから通信したいよ!」とサーバーにリクエストを送ります。
このとき送られるのが「SYN(シンクロナイズ)」という信号。
手順2:サーバー → クライアントへ「SYN-ACK」(許可と応答)
サーバーはそれを受け取って、「いいよ、準備できてるよ」と返事します。
これが「SYN-ACK(シンクロナイズ+応答)」。
手順3:クライアント → サーバーへ「ACK」(最終確認)
クライアントは、サーバーからの返事を確認して「じゃあ始めますね!」と返します。
これが「ACK(確認応答)」です。
Javaでソケット通信を実装してみよう
実際にコードを書いてみるとイメージが掴みやすくなります。ここでは、サーバーとクライアントを別々のJavaクラスとして実装します。
Javaのサーバー側のコード
import java.io.*;
import java.net.*;
public class SimpleServer {
public static void main(String[] args) throws IOException {
ServerSocket serverSocket = new ServerSocket(12345);
System.out.println("サーバーがポート12345で待機中...");
Socket clientSocket = serverSocket.accept();
System.out.println("クライアントが接続しました。");
BufferedReader in = new BufferedReader(new InputStreamReader(clientSocket.getInputStream()));
PrintWriter out = new PrintWriter(clientSocket.getOutputStream(), true);
String inputLine;
while ((inputLine = in.readLine()) != null) {
System.out.println("受信: " + inputLine);
out.println("サーバーからの応答: " + inputLine);
}
in.close();
out.close();
clientSocket.close();
serverSocket.close();
}
}コードのポイント解説
ServerSocket serverSocket = new ServerSocket(12345);
System.out.println("サーバーがポート12345で待機中...");Socket clientSocket = serverSocket.accept();
System.out.println("クライアントが接続しました。");BufferedReader in = new BufferedReader(new InputStreamReader(clientSocket.getInputStream()));
PrintWriter out = new PrintWriter(clientSocket.getOutputStream(), true);String inputLine;
while ((inputLine = in.readLine()) != null) {
System.out.println("受信: " + inputLine);
out.println("サーバーからの応答: " + inputLine);
}Javaのクライアント側のコード
import java.io.*;
import java.net.*;
public class SimpleClient {
public static void main(String[] args) throws IOException {
Socket socket = new Socket("localhost", 12345);
BufferedReader stdIn = new BufferedReader(new InputStreamReader(System.in));
BufferedReader in = new BufferedReader(new InputStreamReader(socket.getInputStream()));
PrintWriter out = new PrintWriter(socket.getOutputStream(), true);
String userInput;
System.out.println("メッセージを入力してください:");
while ((userInput = stdIn.readLine()) != null) {
out.println(userInput);
System.out.println("サーバーから: " + in.readLine());
}
in.close();
out.close();
stdIn.close();
socket.close();
}
}コードのポイント解説
Socket socket = new Socket("localhost", 12345);BufferedReader stdIn = new BufferedReader(new InputStreamReader(System.in));
BufferedReader in = new BufferedReader(new InputStreamReader(socket.getInputStream()));
PrintWriter out = new PrintWriter(socket.getOutputStream(), true);System.out.println("メッセージを入力してください:");
while ((userInput = stdIn.readLine()) != null) {
out.println(userInput);
System.out.println("サーバーから: " + in.readLine());
}in.close();
out.close();
stdIn.close();
socket.close();ソケット通信のポイント
実装してみると、以下の点が重要であることが分かります。
ポイント
- ServerSocketはクライアントからの接続を受け入れる役割
- Socketは接続を行い、InputStream/OutputStreamを使って通信する
- 通信は一方通行ではなく、双方向(送る・受け取る)が可能
- 必ず入出力ストリームを閉じて、リソースを開放すること
ソケットの流れは以下の通りになります。
[ユーザー入力] → [SimpleClient] →→→ [SimpleServer]
(クライアントが入力 → サーバーへ送信 → サーバーが応答 → クライアントが表示)
まとめ:Javaでソケット通信は難しくない
本記事では、Javaにおけるソケット通信の基本から、実際のコードを用いたサーバー・クライアント間のデータ送受信の実装までを体系的に解説しました。
TCPプロトコルの仕組みや3ウェイ・ハンドシェイクの流れ、JavaのSocket・ServerSocketクラスの使い方を一貫して学ぶことで、ネットワーク通信の基礎が自然に身につきます。
【要点まとめ】
- ソケット通信とはネットワーク越しにプログラム同士が通信する仕組み
- サーバーはServerSocketで待ち受け、クライアントはSocketで接続する
- Javaのソケット通信はTCPプロトコルを利用している
- TCPは順序通り・確実にデータを届ける特徴がある
- 接続開始時は3ウェイ・ハンドシェイクが行われる
- サーバー側はaccept()でクライアントの接続を待つ
- クライアント側はユーザー入力を送信し、サーバーからの応答を受信する
- 通信は双方向であり、入力と出力のストリームをそれぞれ使う
- 通信終了時はすべてのリソースを明示的にcloseすることが重要
- サンプルコードを理解することで自作アプリ開発の基礎が築ける
Javaでのソケット通信は、一見とっつきにくく感じるかもしれませんが、仕組みさえ理解してしまえば非常にシンプルです。
サンプルコードを実行しながら、通信の流れを体感することで、ネットワークプログラミングの土台がしっかりと身につきます。