egg-socket和前端Vue的通信

458 阅读3分钟

最近因为要做一个实时传输视频的设备,前端用Vue写的,后端用egg写的。所以,准备使用egg-socket来配置文档。

1.egg中首先按照egg-socket包 npm i --save egg-socket

2.配置socket,在config文件夹中,先在plugin.js中配置包依赖 io: { enable: true, package: 'egg-socket.io', }, 接着打开config.default.js配置 config.io = { namespace: { '/': { //配置中间件接收处理 connectionMiddleware: [ 'auth' ], //处理回来的数据 packetMiddleware: [ 'filter' ], }, },

**//这一步可以不要。如果后面要指定客户端的发送的话,这一步不要写。**

generateId: req => { //自定义 socket.id 生成函数
  const data = qs.parse(req.url.split('?')[1]);
  return data; // custom id must be unique
},

}; 在app下,我们要创建io文件。创建controller文件夹,middleware文件夹。 接下来要在middleware中配置好上面定义的俩个字段的文件夹。 auth.js

/*
 * @Description: 
 * @Author: msq
 * @Date: 2021-06-01 09:06:43
 * @LastEditTime: 2021-06-01 22:27:03
 * @LastEditors: msq
 * @Reference: 
 */
'use strict';
const fs = require('fs')
const path = require('path')
// 这个中间件的作用是提示用户连接与断开的,连接成功的消息发送到客户端,断开连接的消息在服务端打印
module.exports = app => {
  let room =[]
  return function* (next) {
    this.socket.join('all')
     let id = String(this.request.header.referer).split('=')[1]
    console.log(room.length)
    if(room.length>0){
      console.log('hahahahah')
      let flag = false
      flag = room.some(v=>{
        return Number(v.id) === Number(id)
      })
      if(!flag){
        room.push({id,query:this.socket.id})
      }
    }else{
      console.log('sdasdsa')
      room.push({id,query:this.socket.id})
    }
    // console.log(parm)
    console.log(room)
    let file = path.resolve(__dirname, '../../public/s.json')
    fs.appendFile(file,JSON.stringify({id,query:this.socket.id})+'\n', "utf-8", function ( err ) {
      if( err ){
          console.log( "数据追加失败" );
      }else{
          console.log( "数据追加成功" );
      }
  } )
    // console.log('chat 控制器打印', message);
    yield* next;
    console.log('disconnection!');
    console.log('asdasds')
  };
};

filter.js

'use strict';

// 这个中间件的作用是将接收到的数据再发送给客户端
module.exports = app => {
  return function*(next) {
    // this.socket.emit('res', 'packet received!');
    // console.log('packet:', this.packet);
    yield* next;
  };
};

接下来我们可以在controller中写我们的程序.

/*
 * @Description: 
 * @Author: msq
 * @Date: 2021-06-01 09:06:43
 * @LastEditTime: 2021-06-01 22:23:50
 * @LastEditors: msq
 * @Reference: 
 */
'use strict';
const fs = require('fs')
const path = require('path')
// 将收到的消息发送给客户端
module.exports = app => {
  let room = []
  class Controller extends app.Controller {
    async index() {
      const {socket,app, query} = this.ctx
      
    let file = path.resolve(__dirname, '../../public/s.json')
// fs.readFile(file, "utf-8", function(error, data) {
//   console.log(data)
//   console.log(typeof data)
//   // let da = JSON.parse(data)
//   // console.log(error);  //如果err为null就说明读取成功了,没有出错
//   // console.log(data); // 如果不给第二个参数[读取的文件编码格式]就会以beffer格式输出
//   // const d = da.find((v)=>{
//   //   return Number(v.id) === 7
//   // })
//   // console.log(d)
//   // const nsp = app.io.of('/');
//   // nsp.sockets[JSON.parse(data)].emit('res', "hello ");
//   //  用error来判断文件是否读取成功
//   if (error) return console.log("读取文件失败,内容是" + error.message);
//   // console.log("读取文件成功,内容是" + JSON.parse(data));
// });
fs.readFile(file, "utf-8", function(error, data) {
  console.log(data.split('\n'))
  console.log(typeof data)
  let s = []
  let x = data.split('\n')
  x.forEach(v=>{
    if(v != ''){
      s.push(JSON.parse(v))
    }
  })
  console.log(s)
 const nsp = app.io.of('/');
//  console.log(s[0].query)
**//  console.log(nsp.sockets)**
//  console.log('------------')
//  console.log(socket.id)
//  console.log(nsp.sockets)
//  console.log(nsp.sockets[{"EIO":"3","transport":"polling","t":"Nd7gTle"}])
//  console.log('-----------------')
console.log('-----------[')
console.log('-------------')
console.log(**nsp.sockets[s[0].query]**)
// console.log(socket)
socket.to(s[0].query).emit('res','hello')
// socket[s[0].query].emit('res', "hello ");
  // if (error) return console.log("读取文件失败,内容是" + error.message);
  // console.log("读取文件成功,内容是" + JSON.parse(data));
});
    // const id = this.ctx.config.generateId()
    // console.log(id)
    }
  }
  return Controller;
};

nsp.sockets中包含了所有 的客户端连接。如果要指定客户端可以利用 socket.id拿取,然后取到客户端连接。 Vue前端 在Vue中配置的话主要是下载 vue-socket.io和socket.io-client俩个包 首先在main.js中配置

import VueSocketio from 'vue-socket.io';
import socketio from 'socket.io-client';
Vue.use(VueSocketio, socketio(**'http://10.248.124.212:7001**'));
//这里是上面egg项目的后端地址。

接下来我们就可以在页面中使用了。 在页面的中, sockets: {} 跟methods是同级别的。道理是一样的噢。 如果有小伙棒需要源码,可以@我。