websocket协议
- 简介
WebSocket 不是一门技术,而是一种全新的协议。它应用 TCP 的 Socket(套接字),为网络应用定义了一个新的重要的能力:客户端和服务器端的双全工传输和双向通信。是继 Java applets、 XMLHttpRequest、 Adobe Flash,、ActiveXObject、 各类 Comet 技术之后,服务器推送客户端消息的新趋势。
- 与http的关系
在网络分层上,websocket 与 http 协议都是应用层的协议,它们都是基于 tcp 传输层的,但是 websocket 在建立连接时,是借用 http 的 101 switch protocol 来达到协议转换(Upgrade)的,从 HTTP 协议切换成 WebSocket 通信协议,这个动作协议中称“握手”;
握手成功后,websocket 就使用自己的协议规定的方式进行通讯,跟 http 就没有关系了。
PHP 实现 websocket 服务器
-
PHP 实现 websocket 的话,主要是应用 PHP 的 socket 系列函数库,PHP 的 socket 函数库跟 C 语言的 socket 函数非常类似。在 PHP 手册中看一遍 socket 函数,我想大家也能对 php 的 socket 编程有一定的认识。
-
在php中还存在 stream_socket_xxxx 函数簇,stream_socket_xxxx是对socket等等一些函数的封装,提供更易用的api,支持更多的的协议和更多的函数,推荐使用stream,workerman基于此提供了websocket协议的封装和多进程的支持,我们可以直接使用
-
不同于socket__xx和stream_socket_xx,Swoole是一个标准的PHP扩展,内置了WebSocket服务器端,简单几行代码就可以写出一个高性能的异步非阻塞多进程的WebSocket服务器。
workerman实现的websocket服务端
count = 4;
// 进程启动后设置一个每5秒运行一次的定时器
$worker->onWorkerStart = function($worker) {
Timer::add(5, function()use($worker){
$time_now = time();
foreach($worker->connections as $connection) {
// 有可能该connection还没收到过消息,则lastMessageTime设置为当前时间
if (empty($connection->lastMessageTime)) {
$connection->lastMessageTime = $time_now;
continue;
}
// 上次通讯时间间隔大于心跳间隔,则认为客户端已经下线,关闭连接
if ($time_now - $connection->lastMessageTime > HEARTBEAT_TIME) {
$connection->close();
}
}
});
};
// Emitted when new connection come
$ws_worker->onConnect = function($connection)
{
echo "New connection\n";
};
// Emitted when data received
$ws_worker->onMessage = function($connection, $data)
{
var_dump($data);
// Send hello $data
$connection->send('hello ' . $data);
};
// Emitted when connection closed
$ws_worker->onClose = function($connection)
{
echo "Connection closed\n";
};
// Run worker
Worker::runAll();
swoole实现的websocket服务端
set(array(
'worker_num' => 4, //worker process num
'dispatch_mode'=>2,
'heartbeat_idle_time' => 25,//心跳间隔
'heartbeat_check_interval' => 5,//检查间隔
));
$ws->on('open', function ($ws, $request) {
echo "New connection\n";
});
$ws->on('message', function ($ws, $frame) {
echo "{$frame->data}\n";
$ws->push($frame->fd, "hello {$frame->data}");
});
$ws->on('close', function ($ws, $fd) {
echo "client-{$fd} closed\n";
});
$ws->start();
以上就是php实现websocket服务的两种实现方案
workerman 安装
composer require workerman/workerman
swoole 安装
pecl install swoole
websocket客户端
创建客户端
- 前端我们使用 js 调用 Websocket 方法很简单就能创建一个 websocket 连接,服务器会为帮我们完成连接、握手的操作,js 使用事件机制来处理浏览器与服务器的交互:
// 创建一个 websocket 连接
var ws = new WebSocket("ws://127.0.0.1:8080");//请对应服务端端口和ip地址
// websocket 创建成功事件
ws.onopen = function () {
};
// websocket 接收到消息事件
ws.onmessage = function (e) {
var msg = JSON.parse(e.data);
//发送消息
ws.send(msg);
}
// websocket 错误事件
ws.onerror = function () {
};
// websocket 连接关闭事件
ws.onclose = function () {
};
//关闭连接
//ws.close();
发送消息也很简单,直接调用 ws.send(msg) 方法就行了。
- 我们也可使用其他方式实现websocket客户端,比如安卓,ios,windows客户端,这些方案都可以很方便的连接上PHP实现的websocket服务器,可以应用于手机app、移动通讯,微信小程序,手游服务端、网络游戏、PHP聊天室、硬件通讯、智能家居、车联网、物联网等领域