揮発性のメモ2

http://d.hatena.ne.jp/iww/

PHPでネットワークプログラミングをおこなう

PHPTCPソケットを作りどっかに接続してなにか送受信とかする

ソケットを使う

http://jp1.php.net/manual/ja/ref.sockets.php
BSDソケットまんまのAPIを使用する方法

  1. ソケット作成
  2. オプション設定
  3. 接続
  4. 送受信
#!/usr/bin/php
<?
    $host = "192.168.101.10";
    $port = 37564;
    $sndtimeo = 10; // 接続タイムアウト (本当は送信タイムアウト)
    $rcvtimeo = 30; // 受信タイムアウト

    // ソケット作成
    $sd = socket_create( AF_INET, SOCK_STREAM, SOL_TCP );
    // オプション設定
    socket_set_option( $sd, SOL_SOCKET, SO_SNDTIMEO, array("sec"=>$sndtimeo,"usec"=>0) );
    socket_set_option( $sd, SOL_SOCKET, SO_RCVTIMEO, array("sec"=>$rcvtimeo,"usec"=>0) );
    // 接続
    socket_connect( $sd, $host, $port ) or die("socket_connect");
    
    // 送受信
    socket_write( $sd, "ABCDEFG" );
    $buf = socket_read( $sd, 16 );

    print( $buf."\n" );
?>

ソケットは作成直後はブロッキング設定になっています。 このままだと接続待ちや受信待ちで無限に待つのでタイムアウトを設定します。 タイムアウトは送信方向、受信方向でそれぞれ別に設定します。
(この辺はC言語setsockopt()を使うのとおなじ。 一般的に接続タイムアウトは送信タイムアウトと同義なので、PHPでもそれに倣う)

ストリームを使う

http://jp1.php.net/manual/ja/ref.stream.php
汎用的なストリームを使って接続する方法

  1. ストリーム作成(接続)
  2. オプション設定
  3. 送受信
#!/usr/bin/php
<?
    $host = "192.168.101.10";
    $port = 37564;
    $sndtimeo = 10; // 接続タイムアウト (本当は送信タイムアウト)
    $rcvtimeo = 30; // 受信タイムアウト

    // ストリーム作成(接続)
    $fh = stream_socket_client( "tcp://$host:$port", $errno, $errstr, $sndtimeo ) or die("stream_socket_client");
    // オプション設定
    stream_set_timeout( $fh, $rcvtimeo );
    
    // 送受信
    fwrite( $fh, "ABCDEFG" );
    $buf = fread( $fh, 16 );

    print( $buf."\n" );
?>

接続時に接続タイムアウト時間を設定できますが、これは接続時にのみ使用されるため、接続後はあらためて受信タイムアウト時間を設定する必要があります。

得られるリソースがストリームなので、ほかのストリームと区別なく使用することが可能になり便利。 コードもそれなりにすっきりしていい感じ。
stream_socket_client()ではなくfsockopen()でもいいけど、特に利用するメリットはなさそう。