isset($connection->worker->connections[$connection->id])判断下
isset($connection->worker->connections[$connection->id])
<?php use Workerman\Worker; require_once './../Workerman/Autoloader.php'; // 初始化一个worker容器,监听1234端口 global $worker; $worker = new Worker('tcp://0.0.0.0:1235'); // 这里进程数必须设置为1 $worker->count = 1; // 新增加一个属性,用来保存设备id到connection的映射 $worker->deviceIdConnections = array(); // 当有设备发来消息时执行的回调函数 $worker->onMessage = function($connection, $data)use($worker) { // 判断当前设备是否已经验证,既是否设置了device_id if(!isset($connection->device_id)) { // 没验证的话把第一个包当做device_id(这里为了方便演示,没做真正的验证) $device_id = $data; $connection->device_id = $device_id; /* 保存device_id到connection的映射,这样可以方便的通过device_id查找connection, * 实现针对特定device_id推送数据 */ $old_connection = isset($worker->deviceIdConnections[$device_id]) ? $worker->deviceIdConnections[$device_id] : null; $worker->deviceIdConnections[$device_id] = $connection; if ($old_connection) { $old_connection->close(); } else { // ====设备上线==== echo "$device_id 上线\n"; } return; } }; // 当有设备连接断开时 $worker->onClose = function($connection)use($worker) { global $worker; if (!isset($connection->device_id) || !isset($worker->deviceIdConnections[$connection->device_id])) { return; } $device_id = $connection->device_id; $connection_online = $worker->deviceIdConnections[$device_id]; // 连接断开时删除映射 if ($connection->id == $connection_online->id) { unset($worker->deviceIdConnections[$device_id]); // === 设备下线 === echo "$device_id 下线\n"; } }; // 启动 Worker::runAll();
workerman里利用onClose来监控设备下线,例如上面的例子
监听多个设备 用thinkphp的类方法写,有例子吗?
参考上面例子写就行了
@1:大佬,您能帮助我写个tp5的方式吗.我想了半天不知道该怎么弄.....
@1:下面的例子是我写的,您能看着帮我修改一下吗
不会tp
<?php namespace app\push\controller; use think\Db; use think\worker\Server; use Workerman\Lib\Timer; // 心跳间隔55秒 define('HEARTBEAT_TIME', 3); class Worker extends Server { protected $socket = 'http://0.0.0.0:1235'; /** * 收到信息 * @param $connection * @param $data */ public function onMessage($connection, $data) { // dump($connection); $post = $data['request']; dump($post['Data']['DeviceInfo']['DeviceUUID']); switch ($post['Name']) { case 'heartbeatRequest': $return = array( 'Name' => 'heartbeatResponse', 'TimeStamp' => time(), "Code" => 1, "Message" => "" ); $uuid = $post['Data']['DeviceInfo']['DeviceUUID']; $connection->worker->name = $uuid; $this->updateDeviceStatus($uuid, 1); return $return; break; case 'captureInfoRequest': echo 1; break; case 'resultRequest': echo 3; break; } } /** * 当连接建立时触发的回调函数 * @param $connection */ public function onConnect($connection) { } /** * 当连接断开时触发的回调函数 * @param $connection */ public function onClose($connection) { // dump($connection->worker); $uuid = $connection->worker->name; // dump($uuid); $this->updateDeviceStatus($uuid, 0); } /** * 当客户端的连接上发生错误时触发 * @param $connection * @param $code * @param $msg */ public function onError($connection, $code, $msg) { echo "error $code $msg\n"; } /** * 每个进程启动 * @param $worker */ public function onWorkerStart($worker) { Timer::add(1, function () use ($worker) { $time_now = time(); foreach ($worker->connections as $connection) { echo "在线"; // 有可能该connection还没收到过消息,则lastMessageTime设置为当前时间 if (empty($connection->lastMessageTime)) { $connection->lastMessageTime = $time_now; continue; } // 上次通讯时间间隔大于心跳间隔,则认为客户端已经下线,关闭连接 if ($time_now - $connection->lastMessageTime > HEARTBEAT_TIME) { echo "下线"; $connection->close(); } } }); } /** * note: 更改设备状态 * user: 万象初新 * date: 2020/7/28 10:04 */ public function updateDeviceStatus($uuid, $status = 0) { return Db::name('julong_device')->where('uuid', $uuid)->update(array('is_online' => $status)); } }
isset($connection->worker->connections[$connection->id])
判断下workerman里利用onClose来监控设备下线,例如上面的例子
监听多个设备 用thinkphp的类方法写,有例子吗?
参考上面例子写就行了
@1:大佬,您能帮助我写个tp5的方式吗.我想了半天不知道该怎么弄.....
@1:下面的例子是我写的,您能看着帮我修改一下吗
不会tp