php socket(服务器和客户端范例)


php实现异步,用socket是一个不错的选择。

把下面两个文件保存为server.php和client.php,其中server.php可以直接用CLI命令行执行(php server.php),client.php可用http访问。当然全部用cli或全部用http都OK。

server.php

<?php
/**
 * bsykc-20161101-SOCKET通讯
 * 服务端9s
 * 
 */
error_reporting(E_ALL);
set_time_limit(0);
//ob_implicit_flush();
$address = '127.0.0.1';
$port = 31000;//提供服务的端口
//创建服务端口
if( ($handle = socket_create(AF_INET, SOCK_STREAM, SOL_TCP)) === false) {
    //写日志-服务器出错
    echo 'serverError.socket_create()failed:' . socket_strerror(socket_last_error()) . "\n";
    exit();
}
//绑定服务端口
if (socket_bind($handle, $address, $port) === false) {
    //写日志-服务器出错
    echo 'serverError.socket_bind()failed' . socket_strerror(socket_last_error($handle)) . "\n";
    exit();
}
//监听服务端口
if (socket_listen($handle, 5) === false) {
    //写日志-服务器出错
    echo 'serverError.socket_listen()failed:' . socket_strerror(socket_last_error($handle)) . "\n";
    exit();
}

echo 'serverRuning...'."\n";
//遍历接收客户端的信息
do {
    //得到一个链接conn
    if (($conn = socket_accept($handle)) === false) {
        //写日志-服务器出错
        echo 'serverError.socket_accept()failed:'.socket_strerror(socket_last_error($handle)) . "\n";
        exit();
        break;
    }

    //模拟IO等操作延迟返回
    $num = 0;
    /*for($i=0;$i<100000;$i++){$num+= rand(1,2);}*/

    //welcome  发送到客户端
    //$msg = 'serverResponse:'."\n";//返回给客户的信息
    //socket_write($conn, $msg, strlen($msg));//写进缓冲区

    //读取客户端提交的数据
    $result = 'receivedMessage:'."\n";
    echo "\n".'----------clientMessage:'.microtime().'-----------'."\n";
    $buf = socket_read($conn, 8192);
    $result.= $buf;
    echo $result;//
    echo "\n".'----------clientMessage:'.microtime().'-----------'."\n\n";

    //返回给用户
    $result = 'ImServer,thisMessageForYou,serverTime:'.microtime().'NUM='.$num;
    if (false === socket_write($conn, $result, strlen($result))) {
        //写日志-服务器出错
        echo 'serverError.socket_write()failed:' . socket_strerror(socket_last_error($handle)) ."\n";
        exit();
    } else {
        echo 'send2ClientSuccess.';
    }
    socket_close($conn);
    echo "\n\n"."\n\n"."\n\n"."\n\n";
} while(true);

//关闭socket
socket_close($handle);

?>

client.php

<?php
/**
 * bsykc-20161101-SOCKET通讯
 * 客户端9b
 * 
 */
//error_reporting(E_ALL);
echo 'TCP/IP connecting...'.'<br/>';
$addressHost = '127.0.0.1';
$servicePort = 31000;
//创建一个套接字
$socket = socket_create(AF_INET, SOCK_STREAM, SOL_TCP);
if ($socket === false) {
    echo 'clientError.socket_create()failed:' . socket_strerror(socket_last_error()).'<br/>';
    exit();
} else {
    echo 'socketCreateSuccess.'.'<br/>';
}
//创建链接
$result = socket_connect($socket, $addressHost, $servicePort);
if($result === false) {
    echo 'clientError.socket_connect()failed: '. $result . socket_strerror(socket_last_error($socket)).'<br/>';
    exit();
} else {
    echo 'connectSuccess. '.$addressHost.':'.$servicePort.'<br/>';
}
//拼接缓冲数据
$data = 'HEAD / http/1.1'."\n";
$data .= 'HOST: localhost '."\n";
$data .= 'Connection: close';

echo 'sendingHttpHeadRequest ...'.'<br/>';//发送给服务器
socket_write($socket, $data, strlen($data));
echo  'sendSuccess.OK'.'<br/>';//发送成功


//循环遍历返回-可不接收返回-即实现了异步
define('CFG_SOCKET_WAIT', 5);//等待返回时间,如果为0则不等待返回
if (CFG_SOCKET_WAIT > 0){
    echo 'readingResponse:';
    echo '<br/>'.'----------serverMessage:'.microtime().'-----------'.'<br/>';
    $out = '';
    while ($out = socket_read($socket, 8192)) {
    echo $out;
    }
    echo '<br/>'.'----------serverMessage:'.microtime().'-----------'.'<br/><br/>';
}else{
    echo 'CFG_SOCKET_WAIT!=0';
}


echo 'closeingSocket...'.'<br/>';
socket_close($socket);
echo 'closeSuccess,clientTime:'.microtime().'<br/>';


原文链接:https://blog.yongit.com/note/126096.html