WebSocket使用示例

本文共--字 阅读约--分钟 | 浏览: -- Last Updated: 2021-07-03

示例1:记录10次客户端与ws服务器 请求-响应 的耗时。

// index.js
var express = require('express');
var WebSocket = require('ws');

var app = express();

var ws = new WebSocket.Server({port: 8080});

app.use(express.static('./views'))

ws.on('connection', function(socket) {
  socket.on('message', function(msg) {
    console.log('\033[96m got: \033[39m %s', msg);
    socket.send('pong');
  })
});

app.listen(3000);
<!-- views/index.html -->
<!DOCTYPE html>
<html lang="en">
<head>
  <meta charset="UTF-8">
  <meta name="viewport" content="width=device-width, initial-scale=1.0">
  <meta http-equiv="X-UA-Compatible" content="ie=edge">
  <title>Document</title>
</head>
<body>
  <h1>websocket test</h1>
  <div id="latency">
  </div>
  <script>
    var lastMessage;
    var count = 0;
    var ws = new WebSocket('ws://localhost:8080');

    ws.onopen = function() {
      ping();
    }

    ws.onmessage = function(ev) {
      console.log('got: %s', ev.data);
      var p = document.createElement('p');
      p.innerHTML = `<p>第${count}次通信耗时: ${new Date() - lastMessage}ms</p>`
      document.getElementById('latency').appendChild(p);

      if (count < 10) {
        ping();
      }
    }

    function ping() {
      count++;
      lastMessage = new Date();
      ws.send('ping');
    }
  </script>
</body>
</html>

示例2:在一个屏幕上以图片的形式展示所有连接过来的用户鼠标的位置,如果用户的鼠标移动,则在所有的连接的客户端上的都跟着移动,如果用户退出,则在所有的客户端中删除图片以及相关的DOM元素。

// index.js
var express = require('express');
var WebSocket = require('ws');

var app = express();
var positions = {}; // 记录连接过来的用户位置
var total = 0; // 记录连接用户总数
var sockets = [];

var ws = new WebSocket.Server({port: 8080});

app.use(express.static('./views'))

ws.on('connection', function(socket) {
  // 记录每个用户的连接
  sockets[total] = socket;
  socket.id = ++total;
  // 发送所有用户的位置给当前用户 只会在连接建立时发送一次
  socket.send(JSON.stringify(positions));

  // 监听用户发过来的位置信息
  socket.on('message', function (msg) {
    try {
      var pos = JSON.parse(msg);
    } catch (error) {
      return;
    }

    positions[socket.id] = pos; // positions: { 1: { x:6 ,y:7}, ...}

    // 广播位置
    broadcast(JSON.stringify({type: 'position', pos: pos, id: socket.id}));
  })

  // 断开连接时,清除定位信息
  socket.on('close', function () {
    delete positions[socket.id];

    // 广播离开
    broadcast(JSON.stringify({type: 'disconnect', id: socket.id}));
  })

  // 广播函数
  function  broadcast(msg) {
    for(var i = 0, l= sockets.length; i < l; i++) {
      sockets[i].send(msg);
    }
  }
});

app.listen(3000);
<!-- ./views/index.html -->
<!-- ./views/delireba.jpg -->
<!DOCTYPE html>
<html lang="en">
<head>
  <meta charset="UTF-8">
  <meta name="viewport" content="width=device-width, initial-scale=1.0">
  <meta http-equiv="X-UA-Compatible" content="ie=edge">
  <title>Document</title>
</head>
<body>
  <h1>WebSocket cursors</h1>
  <script>
    window.onload = function () {
      var ws = new WebSocket('ws://localhost:8080');

      ws.onopen = function () {
        document.onmousemove = function (ev) {
          // 每次移动发送坐标到服务器
          ws.send(JSON.stringify({x: ev.clientX, y: ev.clientY}))
        }
      }

      var flag;

      ws.onmessage = function (ev) {
        var obj = JSON.parse(ev.data);// 接收到了所有人的位置信息
        // 只有第一次,获取的是所有人的位置信息
        if (!flag) {
          flag = true;
          for(var id in obj) { // { 1: { x:6 ,y:7}, ...}
            move(id, obj[id])
          }
        }else { // 之后的每一次 都是位置的更新或者是有人离开
          // 第一次之后的obj格式就不一样了 { type: 'disconnect', id: 1}
          // { type: 'position', id: 1, pos: {x:6 ,y:7}}
          if ('disconnect' == obj.type) { 
            remove(obj.id); // 有人离开
          }else {
            move(obj.id, obj.pos); // 有人更新
          }
        }
      }
    }

    // 根据其他用户的位置展示光标图样
    // 如果这个光标元素存在在dom中 这个被调用时候 说明是位置的更新
    // 如果不存在,则创建一个, 此时为第一次收到所有位置的时候的调用
    function move (id, pos) {
      var cursorWrap = document.getElementById('div'+ id);

      if(!cursorWrap) {
        cursorWrap = document.createElement('div');
        cursorWrap.style.width = '200px';
        cursorWrap.style.height = '200px';
        cursorWrap.id = 'div'+ id;
        cursorWrap.style.position = 'absolute';
        cursorWrap.style.color = 'pink';
        cursorWrap.innerHTML = `
          <span style="position:absolute;z-index:1">我是${id}号热巴</span>
          <img src="./dilireba.jpg" />
        `;

        document.body.appendChild(cursorWrap);
      }

      cursorWrap.style.left = pos.x + 'px';
      cursorWrap.style.top = pos.y + 'px';
    }

    // 离开的 删除代表的dom元素
    function remove(id) {
      var cursorWrap = document.getElementById('div'+ id);
      cursorWrap.parentNode.removeChild(cursorWrap);
    }
  </script>
</body>
</html>