Swoole Socket网络开发框架,是基于php的libevent和pcntl模块的,并且只能用于Linux/Unix系统下。请先启用pcntl,安装libevent扩展。
pcntl:PHP核心模块已包含了pcntl,只需在编译时加入--enable-pcntl即可,当然也可以用extension扩展
libevent:http://pecl.php.net/package/libevent
编写的类需要继承自TCPServer类,在SwooleSocket包中。目前只提供了单进程异步事件模型,适合用于IO耗时较少的网络服务器程序,比如聊天室。多进程异步模型,多进程同步模型,会在近期提供。基类的代码,请从http://code.google.com/p/swoole/检出
?
<?php require 'TCPServer.php'; class MyServer extends TCPServer { function onRecive($client_id,$data) { $data = trim($data); if($data=="quit") { $this->close($client_id); return true; } elseif($data=='shutdown') { $this->shutdown(); } else { $client_socket_name = stream_socket_get_name($this->client_sock[$client_id],true); echo "Server send response data to client $client_socket_name\n"; $send = date('Y-m-d H:i:s')."$client_socket_name said:$data\n"; $this->sendAll($client_id,$send); } } /** * 发送到所有客户端 * @param $data * @return unknown_type */ function sendAll($client_id,$data) { foreach($this->client_sock as $k=>$sock) { if($k==$client_id) continue; fwrite($sock,$data); } } /** * 发送到某个客户端 * @param $client_id * @param $data * @return unknown_type */ function sendTo($client_id,$data) { fwrite($this->client_sock[$client_id],$data); } function onStart() { echo "Server in running!\n"; } function onConnect($client_id) { $this->sendAll($client_id,"Client $client_id is connected!\n"); } function onClose($client_id) { $this->sendAll($client_id,"Client $client_id is closed!\n"); } function onShutdown() { echo "Server in stop!\n"; } } $server = new MyServer('0.0.0.0',8005); $server->run();?
?
客户端程序
?
<?php class Stdio { static $in; static $out; static $buffer_size = 1024; static function input($h='') { if(!self::$in) self::$in = fopen('php://stdin','r'); if($h) self::output($h); return trim(fread(self::$in,self::$buffer_size)); } static function output($string) { if(!self::$out) self::$out = fopen('php://stdout','w'); return fwrite(self::$out,$string); } } $fp = stream_socket_client('tcp://127.0.0.1:8005',$errno, $errstr); $socket = serialize($fp); if(!$fp) { echo "ERROR: $errno - $errstr<br />\n"; } else { $pid = pcntl_fork(); if($pid==-1) { exit("fork fail!\n"); } //child elseif($pid==0) { var_dump($socket); $fp2 = unserialize($socket); while(!feof($fp2)) { Stdio::output(fgets($fp2, 1024)); } } //parent else { while($string!=="quit") { if(!is_writable($fp)) break; $string = Stdio::input("qq#"); fwrite($fp,$string); } posix_kill($pid, 9); } fclose($fp); }php tcpserver.php 运行服务器程序
php tcpclient.php 运行客户端程序,客户端有2个进程,主进程负责接收输入信息,发送到网络。另一个进程,接收网络信息,显示在屏幕上。