Ruby 2.3.0 リファレンスマニュアル > ライブラリ一覧 > socketライブラリ > Socketクラス > tcp_server_loop
tcp_server_loop(port) {|sock,addr| ...} -> ()
[permalink][rdoc]tcp_server_loop(host, port) {|sock,addr| ...} -> ()
TCP/IP で host:port で待ち受けるサーバ側のソケットを作成し、 新しい接続を受け入れるごとにブロックを呼び出します。
ブロックには新しい接続を表すソケットオブジェクトと、 クライアントアドレスを表す Addrinfo オブジェクトが渡されます。
ブロックの実行が終わってもソケットは close されません。 アプリケーション側が明示的に close する必要があります。
このメソッドはブロックを逐次的に呼び出します。 つまりブロックからリターンするまで次のコネクションを受け入れません。 そのため、同時に複数のクライアントと通信したい場合は スレッドのような並列機構を使う必要があります。
サーバのソケットアドレスを決めるために Addrinfo.getaddrinfo が用いられることに注意してください。 Addrinfo.getaddrinfo は複数のアドレスを返す(IPv4 と IPv6 など) 場合があり、その場合その全てが用いられます。つまり IPv4 と IPv6 の 両方を待ち受けます。getaddrinfo が 0 個のアドレスを返す場合はエラー になります。1つ以上を返した場合にそれが用いられます。
# 逐次的な echo サーバ # 一度に一つのクライアントした取り扱えない require 'socket' Socket.tcp_server_loop(16807) {|sock, client_addrinfo| begin IO.copy_stream(sock, sock) ensure sock.close end } # スレッドを使った echo サーバ # 同時に複数のクライアントを取り扱える # 以下の例だと接続制限がない(つまり接続過剰になりえる)ことに注意 require 'socket' Socket.tcp_server_loop(16807) {|sock, client_addrinfo| Thread.new { begin IO.copy_stream(sock, sock) ensure sock.close end } }
内部的には Socket.tcp_server_sockets で 生成したソケットを Socket.accept_loop で処理しています。
[SEE_ALSO] Socket.tcp_server_sockets, Socket.accept_loop