LoginSignup
1
1

More than 1 year has passed since last update.

Socket 通信の基本をメモる

Last updated at Posted at 2022-03-19

Rubyの非同期タスクスケジューラーを自作するにあたり、ネットワーク通信、特にソケットについて理解を深めておきたいと考えた。

経験上まずは手を動かしてみるのがベストだと考えている。以下の素晴らしい記事が見つかったので自分でもやってみる。

手を動かした中で個人的にメモっておきたいところを残す。

Socketとは

Socketは、ネットワークはプログラムが外部のネットワークと通信する際のインターフェイスとして使われるもの。ファイルとして抽象化される。

Socket通信の種類の例

  • インターネット通信
    • UDP (dgram型)
    • TCP (stream型)
  • プロセス間通信(UNIX domain socket通信)
    • UNIX domain socket dgram (dgram型)
    • UNIX domain socket stream (stream型)
dgramとstreamの違い

関連記事を貼る。

memo. sreamの方が信頼性という面では優れている。

サーバーとなるプロセスがデータを受信する手順

以下インターネット通信の場合。unix domain socket通信の場合は、「ポート」が「ファイル」になる。

  1. ソケットを生成する(複数可能)
    • ソケットを初期化する
    • そのソケットを一つのポートにバインドする
    • [stream型のソケットの場合のみ]ソケットを通してポートをリッスンする。
  2. クライアントからのデータ受信を無限ループする
    • IO::select で、ソケットに張り付き、データが到着したソケットを検知する。
    • [ストリーム型のソケットの場合のみ] Socket#accept で、そのソケットのクライアントとのconnectionをアクセプトする
    • そのソケットに入っているデータを読み出す。
    • [ストリーム型のソケットの場合のみ] Socket#close で、connectionをclose する。

終了後は、ソケットをcloseすることを忘れずに。

クライアントとなるプロセスがデータを送信する手順

  1. ソケットを生成する
  2. ソケット経由でデータを書き込む。
    • ストリーム通信のソケットの場合には、Socket#connect(送信先)でコネクションを確立してから、Socket#write(データ)を使用する。
    • データグラム通信のソケットの場合には、Socket#send(データ, 送信先)を使用する。

Rubyでの実装

を参照すると良い。以下の通信が実装されている。

  • internet❎dgram
    • Socket.new(:INET, :DGRAM)でソケット生成
    • UDPSocket.newでもソケット生成可能
  • internet❎stream
    • Socket.new(:INET, :DGRAM)でソケット生成
    • TCPSocket.newでもソケット生成可能
    • TCPServer.newでもソケット生成+listenが可能
  • unix_domain_socket❎dgram
    • Socket.new(:UNIX, :DGRAM)でソケット生成
  • unix_domain_socket❎stream
    • Socket.new(:UNIX, :DGRAM)でソケット生成
    • UNIXSocket.newでもソケット生成が可能
    • UNIXServer.newでもソケット生成+listenが可能

Ref.

メモ
  • ストリーム型のsocketには、Socket#write
追記

https://docs.ruby-lang.org/ja/latest/class/Socket.html#I_ACCEPT_NONBLOCK に書いてあった。

ソケットオブジェクトを生成する汎用的な方法として Socket.new がありますが、以下のようなより便利なメソッドがあります。

  • TCP のクライアントソケット Socket.tcp TCPSocket.open
  • TCP のサーバソケット Socket.tcp_server_loop, Socket.tcp_server_sockets, TCPServer.open
  • UNIX socket のクライアントソケット Socket.unix UNIXSocket.open
  • UNIX socket のサーバソケット Socket.unix_server_loop, Socket.unix_server_socket, UNIXServer.open

また、クライアントソケットは Addrinfo#connect で、サーバソケットを Addrinfo#bind や Addrinfo#listen で作ることもできます。

1
1
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
1
1