工業製造
産業用モノのインターネット | 工業材料 | 機器のメンテナンスと修理 | 産業プログラミング |
home  MfgRobots >> 工業製造 >  >> Industrial programming >> Java

Javaネットワークプログラミング入門: java.netでソケット通信・TCP/UDP・ServerSocket/InetAddressをマスター

ネットワークプログラミングとは、複数のデバイス(コンピュータ)上で実行されるプログラムを書くことを指し、これらのデバイスはネットワークを使用して互いに接続されています。

J2SE APIのjava.netパッケージには、低レベル通信の詳細を提供するクラスとインターフェースのコレクションが含まれており、手元の問題解決に集中できるプログラムを書くことができます。

java.netパッケージは2つの一般的なネットワークプロトコルをサポートしています。

この章では以下の2つのテーマについて理解を深めます。

ソケットプログラミング

ソケットはTCPを使用して2台のコンピュータ間の通信メカニズムを提供します。クライアントプログラムは通信の自分の端でソケットを作成し、そのソケットをサーバーに接続しようと試みます。

接続が確立されると、サーバーは通信の自分の端でソケットオブジェクトを作成します。クライアントとサーバーはソケットへの書き込みと読み取りによって通信できます。

java.net.Socketクラスはソケットを表し、java.net.ServerSocketクラスはサーバープログラムがクライアントを待ち受け、接続を確立するメカニズムを提供します。

ソケットを使用して2台のコンピュータ間でTCP接続を確立する際、以下の手順が実行されます。

接続が確立された後、I/Oストリームを使用して通信が行われます。各ソケットにはOutputStreamとInputStreamの両方があります。クライアントのOutputStreamはサーバーのInputStreamに接続され、クライアントのInputStreamはサーバーのOutputStreamに接続されます。

TCPは双方向通信プロトコルであるため、データを両方のストリームで同時に送信できます。ソケットを実装するための完全なメソッドセットを提供する有用なクラスは以下の通りです。

ServerSocketクラスのメソッド

java.net.ServerSocketクラスは、サーバーアプリケーションがポートを取得し、クライアント要求を待ち受けるために使用されます。

ServerSocketクラスには4つのコンストラクタがあります。

No.メソッドと説明
1public ServerSocket(int port) throws IOException - 指定ポートにバインドされたサーバーソケットの作成を試みる。ポートが他のアプリケーションによって既にバインドされている場合は例外が発生。
2public ServerSocket(int port, int backlog) throws IOException - 前のコンストラクタと類似。backlogパラメータは待ち行列に格納する着信クライアント数を指定。
3public ServerSocket(int port, int backlog, InetAddress address) throws IOException - 前のコンストラクタと類似。InetAddressパラメータはバインドするローカルIPアドレスを指定。複数のIPアドレスを持つサーバーで、どのIPアドレスでクライアント要求を受け付けるかを指定するために使用。
4public ServerSocket() throws IOException - 未バインドのサーバーソケットを作成。このコンストラクタを使用する場合、サーバーソケットをバインドする準備ができたらbind()メソッドを使用。

ServerSocketコンストラクタが例外をスローしない場合、アプリケーションが指定ポートに正常にバインドされ、クライアント要求の準備ができたことを意味します。

ServerSocketクラスの一般的なメソッド:

No.メソッドと説明
1public int getLocalPort() - サーバーソケットが待ち受けているポートを返す。コンストラクタでポート番号として0を渡し、サーバーにポートを見つけさせた場合に有用。
2public Socket accept() throws IOException - 着信クライアントを待機。指定ポートでクライアントがサーバーに接続するか、ソケットがタイムアウトするまで(setSoTimeout()でタイムアウト値が設定されている場合)ブロック。それ以外の場合は無期限にブロック。
3public void setSoTimeout(int timeout) - accept()でサーバーソケットがクライアントを待機する時間のタイムアウト値を設定。
4public void bind(SocketAddress host, int backlog) - SocketAddressオブジェクトで指定されたサーバーとポートにソケットをバインド。引数なしコンストラクタでServerSocketをインスタンス化した場合に使用。

ServerSocketがaccept()を呼び出すと、クライアントが接続するまでメソッドは返りません。クライアントが接続すると、ServerSocketは未指定のポートで新しいSocketを作成し、この新しいSocketへの参照を返します。クライアントとサーバーの間でTCP接続が確立され、通信を開始できます。

Socketクラスのメソッド

java.net.Socketクラスは、クライアントとサーバーの両方が互いに通信するために使用するソケットを表します。クライアントはSocketオブジェクトをインスタンス化して取得し、サーバーはaccept()メソッドの戻り値からSocketオブジェクトを取得します。

Socketクラスにはクライアントがサーバーに接続するための5つのコンストラクタがあります。

No.メソッドと説明
1public Socket(String host, int port) throws UnknownHostException, IOException - 指定されたサーバーの指定ポートに接続を試みる。このコンストラクタが例外をスローしない場合、接続は成功しクライアントはサーバーに接続される。
2public Socket(InetAddress host, int port) throws IOException - 前のコンストラクタと同一だが、ホストがInetAddressオブジェクトで指定される。
3public Socket(String host, int port, InetAddress localAddress, int localPort) throws IOException - 指定ホストとポートに接続し、ローカルホストの指定アドレスとポートにソケットを作成。
4public Socket(InetAddress host, int port, InetAddress localAddress, int localPort) throws IOException - 前のコンストラクタと同一だが、ホストが文字列ではなくInetAddressオブジェクトで指定される。
5public Socket() - 未接続ソケットを作成。このソケットをサーバーに接続するにはconnect()メソッドを使用。

Socketコンストラクタが返ると、単にSocketオブジェクトをインスタンス化するだけでなく、実際に指定されたサーバーとポートへの接続を試みます。

Socketクラスの注目すべきメソッドをいくつか示します。クライアントとサーバーの両方がSocketオブジェクトを持つため、これらのメソッドは両方から呼び出せます。

No.メソッドと説明
1public void connect(SocketAddress host, int timeout) throws IOException - ソケットを指定ホストに接続。引数なしコンストラクタでSocketをインスタンス化した場合にのみ必要。
2public InetAddress getInetAddress() - このソケットが接続されている相手コンピュータのアドレスを返す。
3public int getPort() - リモートマシンでソケットがバインドされているポートを返す。
4public int getLocalPort() - ローカルマシンでソケットがバインドされているポートを返す。
5public SocketAddress getRemoteSocketAddress() - リモートソケットのアドレスを返す。
6public InputStream getInputStream() throws IOException - ソケットの入力ストリームを返す。入力ストリームはリモートソケットの出力ストリームに接続される。
7public OutputStream getOutputStream() throws IOException - ソケットの出力ストリームを返す。出力ストリームはリモートソケットの入力ストリームに接続される。
8public void close() throws IOException - ソケットを閉じる。このSocketオブジェクトはもはやどのサーバーにも再接続できなくなる。

InetAddressクラスのメソッド

このクラスはインターネットプロトコル(IP)アドレスを表します。ソケットプログラミングで必要となる有用なメソッドは以下の通りです。

No.メソッドと説明
1static InetAddress getByAddress(byte[] addr) - 生のIPアドレスからInetAddressオブジェクトを返す。
2static InetAddress getByAddress(String host, byte[] addr) - 提供されたホスト名とIPアドレスに基づいてInetAddressを作成。
3static InetAddress getByName(String host) - ホスト名からホストのIPアドレスを決定。
4String getHostAddress() - テキスト表現でIPアドレス文字列を返す。
5String getHostName() - このIPアドレスのホスト名を取得。
6static InetAddress getLocalHost() - ローカルホストを返す。
7String toString() - このIPアドレスをStringに変換。

ソケットクライアント例

以下のGreetingClientは、ソケットを使用してサーバーに接続し、挨拶を送信してから応答を待機するクライアントプログラムです。

例

// File Name GreetingClient.java
import java.net.*;
import java.io.*;

public class GreetingClient {
    public static void main(String[] args) {
        String serverName = args[0];
        int port = Integer.parseInt(args[1]);

        try {
            System.out.println("Connecting to " + serverName + " on port " + port);
            Socket client = new Socket(serverName, port);
            System.out.println("Just connected to " + client.getRemoteSocketAddress());

            OutputStream outToServer = client.getOutputStream();
            DataOutputStream out = new DataOutputStream(outToServer);
            out.writeUTF("Hello from " + client.getLocalSocketAddress());

            InputStream inFromServer = client.getInputStream();
            DataInputStream in = new DataInputStream(inFromServer);
            System.out.println("Server says " + in.readUTF());

            client.close();
        } catch (IOException e) {
            e.printStackTrace();
        }
    }
}

ソケットサーバー例

以下のGreetingServerプログラムは、コマンドライン引数で指定されたポート番号でクライアントを待ち受けるサーバーアプリケーションの例です。

例

// File Name GreetingServer.java
import java.net.*;
import java.io.*;

public class GreetingServer extends Thread {
    private ServerSocket serverSocket;

    public GreetingServer(int port) throws IOException {
        serverSocket = new ServerSocket(port);
        serverSocket.setSoTimeout(10000);
    }

    public void run() {
        while (true) {
            try {
                System.out.println("Waiting for client on port " + serverSocket.getLocalPort() + "...");
                Socket server = serverSocket.accept();
                System.out.println("Just connected to " + server.getRemoteSocketAddress());

                DataInputStream in = new DataInputStream(server.getInputStream());
                System.out.println(in.readUTF());

                DataOutputStream out = new DataOutputStream(server.getOutputStream());
                out.writeUTF("Thank you for connecting to " + server.getLocalSocketAddress() + "\nGoodbye!");

                server.close();
            } catch (SocketTimeoutException s) {
                System.out.println("Socket timed out!");
                break;
            } catch (IOException e) {
                e.printStackTrace();
                break;
            }
        }
    }

    public static void main(String[] args) {
        int port = Integer.parseInt(args[0]);
        try {
            Thread t = new GreetingServer(port);
            t.start();
        } catch (IOException e) {
            e.printStackTrace();
        }
    }
}

クライアントとサーバーをコンパイルし、サーバーを以下のように起動します。

$ java GreetingServer 6066
Waiting for client on port 6066...

クライアントプログラムを以下のように確認します。

出力

$ java GreetingClient localhost 6066
Connecting to localhost on port 6066
Just connected to localhost/127.0.0.1:6066
Server says Thank you for connecting to /127.0.0.1:6066
Goodbye!

Java

  1. Java演算子をマスター:種類、構文、実践例
  2. Javaコメント:種類、使い方、ベストプラクティス
  3. Java拡張forループをマスター:構文、例、ベストプラクティス
  4. Java文字列をマスター:生成、メソッド、ベストプラクティス
  5. Javaインターフェース完全ガイド:概念、実装、ベストプラクティス
  6. Java無名インナークラス完全ガイド:定義、構文、実践例
  7. Javaのtry-with-resourcesをマスターする:自動リソース管理の仕組みと活用法
  8. Javaアノテーション完全ガイド:種類、配置場所、実践例
  9. Javaアサーション完全ガイド:バグ早期発見とコード信頼性の向上
  10. Java Vectorの理解:使い方、特徴、ArrayListとの比較
  11. Javaネットワークプログラミング入門: java.netでソケット通信・TCP/UDP・ServerSocket/InetAddressをマスター