swoole、websocket搭建聊天室【class swoole_websocket_server not found】

class swoole_websocket_server not found一般为版本问题,建议1.10以上

编译安装

Swoole扩展是按照PHP标准扩展构建的。使用phpize来生成编译检测脚本,./configure来做编译配置检测,make进行编译,make install进行安装。

  • 请下载releases版本的swoole,直接从github主干上拉取最新代码可能会编译不过

  • 如果当前用户不是root,可能没有PHP安装目录的写权限,安装时需要sudo或者su

  • 如果是在git分支上直接git pull更新代码,重新编译前务必要执行make clean

安装准备【一般都能满足】

安装swoole前必须保证系统已经安装了下列软件

php-5.3.10 或更高版本
gcc-4.4 或更高版本
make
autoconf
pcre (centos系统可以执行命令:yum install pcre-devel)

下载地址

下载源代码包后,在终端进入源码目录,执行下面的命令进行编译和安装

cd swoole
phpize
./configure
make
sudo make install

配置php.ini

编译安装成功后,修改php.ini加入

extension=swoole.so

通过php -m或phpinfo()来查看是否成功加载了swoole,如果没有可能是php.ini的路径不对,可以使用php --ini来定位到php.ini的绝对路径。

以下为demo:分别为index.php【默认访问】,websocket.php【运行监听】,client.php 和server.php

index.php

<!DOCTYPE html>
<html>
<head>
    <title>一个简单的聊天室</title>
    <meta charset="UTF-8">
    <script type="text/javascript">
        if(window.WebSocket){
            var webSocket = new WebSocket("ws://119.29.**.**:9501");
            webSocket.onopen = function (event) {
                //webSocket.send("Hello,WebSocket!");
            };
            webSocket.onmessage = function (event) {
                var content = document.getElementById('content');
                if(event.data instanceof Blob) {
                    var img = document.createElement("img");
                    img.src = window.URL.createObjectURL(event.data);
                    content.appendChild(img);
                }else {
                    content.innerHTML = content.innerHTML.concat('<p style="margin-left:20px;height:20px;line-height:20px;">'+event.data+'</p>');
                }
            };
 
            var sendMessage = function(){
                var data = document.getElementById('message').value;
                webSocket.send(data);
                document.getElementById('message').value = '';
            }
        }else{
            console.log("您的浏览器不支持WebSocket");
        }
 
        //检测回车点击
        document.onkeydown=function(event) {
            var e = event ? event : (window.event ? window.event : null);
            if(e.keyCode==13){
                sendMessage();
            }
        }
    </script>
</head>
<body>
<div style="width:600px;margin:0 auto;border:1px solid #ccc;">
    <div id="content" style="overflow-y:auto;height:300px;"></div>
    <hr/>
    <div style="height:40px">
        <input type="text" id="message" style="margin-left:10px;height:25px;width:490px;">
        <button style="height:28px;width:75px;">发送</button>
    </div>
</div>
</body>
</html>

websocket.php

<?php
ignore_user_abort(); // 后台运行
set_time_limit(0); // 取消脚本运行时间的超时上限
 
//创建一个websocket服务器
$ws_server = new swoole_websocket_server('0.0.0.0', 9501);
 
//创建一个用于存储的redis
$redis = new Redis();
$redis->connect('127.0.0.1', 6379);
 
$ws_server->on('open', function ($ws, $request) use ($redis) {
    $redis->sAdd('id', $request->fd);
    $mes = '用户:'.$request->fd.'已加入聊天室';
    $redis->sAdd('mes', $mes);
    pushAll($redis,$ws,$mes);
    getAllMes($redis,$ws);
});
 
$ws_server->on('message', function ($ws, $frame) use ($redis) {
    $mes = '用户:'.$frame->fd.'<br/>'.$frame->data;
    pushAll($redis,$ws,$mes);
});
 
//监听WebSocket连接关闭事件
$ws_server->on('close', function ($ws, $fd) use ($redis) {
        $redis->srem('key:'.$id,$fd);
    $mes = '用户:'.$fd.'已退出聊天室';
    $redis->sAdd('mes', $mes);
    pushAll($redis,$ws,$mes);
});
 
$ws_server->start();
 
/**
 * 登录时获取以前的消息
 */
function getAllMes($redis,$ws){
    $mesLists = $redis->sMembers('mes');
    foreach ($mesLists as $mes){
        pushAll($redis,$ws,$mes);
    }
}
/**
 * 给所有用户发信息
 */
function pushAll($redis,$ws,$mes){
    $fds = $redis->sMembers('id');
    foreach ($fds as $fd){
            if($ws->exist($fd)){
                    $ws->push($fd,$mes);
            }
    }
}


client.php

<?php
 
/**
 * Class Client
 * 基础客户端
 * 作用:可以在Service开启后向Service发送语句(感觉没什么用)
 */
class Client{
        private $client;
 
    /**
     * Client constructor.
     * 开启一个实例
     */
        public function __construct() {
                $this->client = new swoole_client(SWOOLE_SOCK_TCP);
        }
         
    public function connect() {
        if( !$this->client->connect("127.0.0.1", 9501 , 1) ) {
            echo "错误: {$this->client->errMsg}[{$this->client->errCode}]\n";
        }
        echo "获得信息来自:{$this->client->recv()}\n";
        while(1){
            fwrite(STDOUT, "请输入消息");
            $msg = trim(fgets(STDIN));
            $this->client->send( $msg );
        }
 
    }
}
 
$client = new Client();
$client->connect();

server.php

<?php
 
/**
 * Class Server
 * 开启一个swoole服务端
 * 作用:监听端口,发送信息,接收信息,关闭消息
 */
class Server{
    private $serv;
 
    public function __construct() {
        $this->serv = new swoole_server("0.0.0.0", 9501);
        $this->serv->set(array(
            'worker_num' => 8,
            'daemonize' => false,
            'max_request' => 10000,
            'dispatch_mode' => 2,
            'debug_mode'=> 1
        ));
 
        $this->serv->on('Start', array($this, 'onStart'));
        $this->serv->on('Connect', array($this, 'onConnect'));
        $this->serv->on('Receive', array($this, 'onReceive'));
        $this->serv->on('Close', array($this, 'onClose'));
 
        $this->serv->start();
    }
    //开始
    public function onStart( $serv ) {
        echo "服务已启动\n";
    }
    //获得的信息
    public function onConnect( $serv, $fd, $from_id ) {
        $serv->send( $fd, "你好 {$fd}!" );
    }
    //获得的信息
    public function onReceive( swoole_server $serv, $fd, $from_id, $data ) {
        echo "获得来自客户 {$fd}的消息:{$data}\n";
    }
 
    public function onClose( $serv, $fd, $from_id ) {
        echo "客户 {$fd} 退出了服务\n";
    }
}
// 启动服务器
$server = new Server();

Linux运行

php webcoket.php

即可

nba2k2球员数据
请先登录后发表评论
  • 最新评论
  • 总共0条评论