123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211 |
- var server = require("http").createServer();
- const TLSSigAPIv2 = require('tls-sig-api-v2')
- const appids = require('./../config/appid')
- const api = new TLSSigAPIv2.Api(appids.shop.appid, appids.shop.key)
- function getSig (userId) {
- return api.genSig(userId, 86400)
- }
- const EVENT = {
- someOneInRoom: 'someOneInRoom',
- someOneLeaveRoom: 'someOneLeaveRoom',
- startCall: 'startCall',
- stopCall: 'stopCall',
- webSyncAction: 'webSyncAction',
- clientSyncAction: 'clientSyncAction',
- action: 'action',
- roomClose: 'roomClose',
- roomIn: 'roomIn',
- changeVoiceStatus: 'changeVoiceStatus'
- }
- const CODEMAP = {
- 3001: '房间已被解散',
- 3002: '房主主动解散'
- }
- module.exports = class WebSocketServer {
- constructor() {
- this._pageMap = new Map();
- this._roomIDS = new Map();
- this._roomPerson = new Map()
- }
- create() {
- this.io = require("socket.io")(server, {
- path: "/vr-node",
- serveClient: false,
- // below are engine.IO options
- pingInterval: 10000,
- pingTimeout: 5000,
- cookie: false,
- });
- server.listen(3030, { origins: "*" });
- this.io.on("connection", (socket) => {
- let user = socket.handshake.query
- const { roomId, userId, sceneNum, isClient, role, userLimitNum } = user
- const webRoomId = `${roomId}_${sceneNum}_web`
- const clientRoom = userId ? `${userId}` : `${userId}${roomId}`
- // 加入客户端与H5单独的通讯房间
- socket.join(clientRoom, () => {
- })
- socket.on(EVENT.clientSyncAction, (data) => {
- socket.broadcast.to(clientRoom).emit(EVENT.clientSyncAction, data)
- })
- socket.on(EVENT.changeVoiceStatus, data => {
- let _roomPerson = this._roomPerson.get(roomId) || []
- user.voiceStatus = data.status
- _roomPerson.forEach(item => {
- if (item.userId === user.userId) {
- item.voiceStatus = user.voiceStatus
- }
- })
- this._roomPerson.set(roomId, _roomPerson)
- socket.broadcast.to(roomId).emit(EVENT.changeVoiceStatus, {roomsPerson: sortRoomUser(_roomPerson)})
- })
-
- // 若有房间人数限制
- if (userLimitNum && this._roomPerson.get(roomId) && sortRoomUser(this._roomPerson.get(roomId)).length >= userLimitNum) {
- // console.log(this._roomPerson.get(roomId), 'full')
- // console.log(this._roomPerson.get(roomId).length, userLimitNum, 'full')
- setTimeout(() => {
- socket.emit('roomInFail', { type: 'full', msg: '房间人数已满' })
- }, 1000)
- return this
- }
-
- // 若已结束、房间已关闭
- if ( user.role !== 'leader'&& ((this._roomPerson.get(roomId) && !this._roomPerson.get(roomId).find(item => item.role === 'leader')) || (!this._roomPerson.get(roomId)))) {
- console.log('roomClose')
- setTimeout(() => {
- socket.emit(EVENT.roomClose, { code: 3001, msg: CODEMAP[3001]})
- }, 1000)
- return this
- }
- // 加入所有连接数的通讯房间
- socket.join(roomId, () => {
- // 只有h5才能加入H5端的房间
- if (!isClient) {
- let roomsPerson = this._roomPerson.get(roomId) || []
- if (userId) {
- user.sig = getSig(userId)
- }
- let clientPerson = this._roomPerson.get(clientRoom) || []
- clientPerson.forEach(item => {
- if (item.userId === user.userId && item.avatar) {
- user.avatar = item.avatar
- user.voiceStatus = item.voiceStatus
- }
- })
- roomsPerson.push(user)
- this._roomPerson.set(roomId, roomsPerson)
- }
- })
- let clientPerson = this._roomPerson.get(clientRoom) || []
- if (isClient) {
- clientPerson.push(user)
- this._roomPerson.set(clientRoom, clientPerson)
- }
-
- if (!isClient) {
- socket.join(webRoomId, () => {
- // let roomsPerson = this._roomPerson.get(roomId) || []
- // socket.broadcast.to(roomId).emit(EVENT.someOneInRoom, { user, roomsPerson: sortRoomUser(roomsPerson) })
- })
- }
- socket.on(EVENT.startCall, () => {
- if (!isClient) {
- let roomsPerson = this._roomPerson.get(roomId) || []
- console.log('startCall', sortRoomUser(roomsPerson) )
- socket.emit(EVENT.roomIn, { roomsPerson: sortRoomUser(roomsPerson) })
- socket.broadcast.to(roomId).emit(EVENT.someOneInRoom, { user, roomsPerson: sortRoomUser(roomsPerson) })
- }
- })
- socket.on(EVENT.stopCall, () => {
- socket.leave(roomId)
- if (role === 'leader') {
- socket.broadcast.to(roomId).emit(EVENT.roomClose, { code: 3002, msg: CODEMAP[3002]})
- }
- if (!isClient) {
- console.log('stopCall', user)
- // socket.leave(webRoomId)
- let roomsPerson = this._roomPerson.get(roomId) || []
- roomsPerson = removeRoomUser(roomsPerson, user)
- this._roomPerson.set(roomId, roomsPerson)
- socket.broadcast.to(roomId).emit(EVENT.someOneLeaveRoom, { user, roomsPerson: sortRoomUser(roomsPerson) })
- }
- })
- socket.on(EVENT.webSyncAction, (data) => {
- socket.broadcast.to(webRoomId).emit(EVENT.webSyncAction, data)
- })
- socket.on(EVENT.action, (data) => {
- socket.broadcast.to(roomId).emit(EVENT.action, data)
- })
- socket.on("disconnect", (reason) => {
- socket.leave(roomId)
- if (!isClient) {
- // if (role === 'leader' && reason !== 'ping timeout') {
- // socket.broadcast.to(roomId).emit(EVENT.roomClose)
- // }
- let roomsPerson = this._roomPerson.get(roomId) || []
- roomsPerson = removeRoomUser(roomsPerson, user)
- this._roomPerson.set(roomId, roomsPerson)
- // socket.broadcast.to(roomId).emit(EVENT.someOneLeaveRoom, { user, roomsPerson })
- socket.leave(webRoomId)
- socket.leave(roomId)
- }
- })
- socket.on('reconnect', () => {
- socket.join(roomId)
- if (!isClient) {
- let roomsPerson = this._roomPerson.get(roomId) || []
- roomsPerson.push(user)
- this._roomPerson.set(roomId, roomsPerson)
- socket.join(webRoomId)
- socket.join(roomId)
- }
- })
- socket.on("error", function (reason) {
- console.log("异常关闭", reason)
- })
- return this;
- })
- }
- close() {
- this.server.disconnect(true);
- }
- };
- function removeRoomUser (roomsPerson, user) {
- for (let i = 0; i < roomsPerson.length; i++) {
- if (roomsPerson[i].userId === user.userId) {
- roomsPerson.splice(i, 1)
- }
- }
- return roomsPerson
- }
- function sortRoomUser (roomsPerson) {
- const res = new Map()
- return roomsPerson.filter((a) => !res.has(a.userId) && res.set(a.userId, 1))
- }
|