restructure realtime server for clarity

This commit is contained in:
Connor Turland 2016-10-18 19:46:34 -04:00
parent d8cd536a95
commit 5921513c79
14 changed files with 396 additions and 4231 deletions

BIN
.env.swp

Binary file not shown.

File diff suppressed because one or more lines are too long

View file

@ -1,23 +0,0 @@
function SocketIoConnection(config) {
this.connection = io.connect(config.url, config.socketio);
}
SocketIoConnection.prototype.on = function (ev, fn) {
this.connection.on(ev, fn);
};
SocketIoConnection.prototype.emit = function () {
this.connection.emit.apply(this.connection, arguments);
};
SocketIoConnection.prototype.removeAllListeners = function () {
this.connection.removeAllListeners();
};
SocketIoConnection.prototype.getSessionid = function () {
return this.connection.socket.sessionid;
};
SocketIoConnection.prototype.disconnect = function () {
return this.connection.disconnect();
};

View file

@ -1,4 +1,4 @@
/* global Metamaps, $, SocketIoConnection */
/* global Metamaps, $ */
/*
* Metamaps.Realtime.js
@ -15,6 +15,7 @@
import _ from 'lodash'
import SimpleWebRTC from 'simplewebrtc'
import SocketIoConnection from 'simplewebrtc/socketioconnection'
import Active from '../Active'
import GlobalUI from '../GlobalUI'
@ -99,6 +100,7 @@ import {
leaveCall,
sendMapperInfo,
sendCoords,
createMessage,
dragTopic,
createTopic,
updateTopic,
@ -510,6 +512,7 @@ const sendables = [
['leaveCall',leaveCall],
['sendMapperInfo',sendMapperInfo],
['sendCoords',sendCoords],
['createMessage',createMessage],
['dragTopic',dragTopic],
['createTopic',createTopic],
['updateTopic',updateTopic],

View file

@ -1,6 +1,8 @@
// create global references
import _ from 'underscore'
import io from 'socket.io-client'
import Metamaps from './Metamaps'
window._ = _
window.io = io
window.Metamaps = Metamaps

View file

@ -40,7 +40,7 @@
"react-dom": "15.3.2",
"react-dropzone": "3.6.0",
"simplewebrtc": "2.2.0",
"socket.io": "0.9.12",
"socket.io": "1.3.7",
"underscore": "1.4.4",
"webpack": "1.13.2"
},

80
realtime/global.js Normal file
View file

@ -0,0 +1,80 @@
import {
// server sendable, client receivable
TOPIC_UPDATED,
TOPIC_DELETED,
SYNAPSE_UPDATED,
SYNAPSE_DELETED,
LIVE_MAPS_RECEIVED,
MAP_WENT_LIVE,
MAP_CEASED_LIVE,
MAP_UPDATED,
// server receivable, client sendable
REQUEST_LIVE_MAPS,
JOIN_MAP,
LEAVE_MAP,
UPDATE_TOPIC,
DELETE_TOPIC,
UPDATE_SYNAPSE,
DELETE_SYNAPSE,
UPDATE_MAP
} from '../frontend/src/Metamaps/Realtime/events'
const adjustAndBroadcast = (io, socket, state, event, data) => {
if (event === JOIN_MAP) {
if (!state.liveMaps[data.mapid]) {
state.liveMaps[data.mapid] = data.map // { name: '', desc: '', numTopics: '' }
state.liveMaps[data.mapid].mapper_count = 1
io.sockets.emit(MAP_WENT_LIVE, state.liveMaps[data.mapid])
}
else {
state.liveMaps[data.mapid].mapper_count++
}
}
else if (event === LEAVE_MAP) {
const mapid = socket.mapid
if (state.liveMaps[mapid] && state.liveMaps[mapid].mapper_count == 1) {
delete state.liveMaps[mapid]
io.sockets.emit(MAP_CEASED_LIVE, { id: mapid })
}
else if (state.liveMaps[mapid]) {
state.liveMaps[mapid].mapper_count--
}
}
}
module.exports = function (io, state) {
io.on('connection', function (socket) {
socket.on(REQUEST_LIVE_MAPS, function (activeUser) {
//constrain response to maps visible to user
var maps = Object.keys(state.liveMaps).map(function(key) { return state.liveMaps[key] })
socket.emit(LIVE_MAPS_RECEIVED, maps)
})
socket.on(JOIN_MAP, data => adjustAndBroadcast(io, socket, state, JOIN_MAP, data))
socket.on(LEAVE_MAP, () => adjustAndBroadcast(io, socket, state, LEAVE_MAP))
socket.on('disconnect', () => adjustAndBroadcast(io, socket, state, LEAVE_MAP))
socket.on(UPDATE_TOPIC, function (data) {
socket.broadcast.emit(TOPIC_UPDATED, data)
})
socket.on(DELETE_TOPIC, function (data) {
socket.broadcast.emit(TOPIC_DELETED, data)
})
socket.on(UPDATE_SYNAPSE, function (data) {
socket.broadcast.emit(SYNAPSE_UPDATED, data)
})
socket.on(DELETE_SYNAPSE, function (data) {
socket.broadcast.emit(SYNAPSE_DELETED, data)
})
socket.on(UPDATE_MAP, function (data) {
socket.broadcast.emit(MAP_UPDATED, data)
})
})
}

62
realtime/junto.js Normal file
View file

@ -0,0 +1,62 @@
import {
INVITED_TO_CALL,
INVITED_TO_JOIN,
CALL_ACCEPTED,
CALL_DENIED,
INVITE_DENIED,
CALL_IN_PROGRESS,
CALL_STARTED,
MAPPER_JOINED_CALL,
MAPPER_LEFT_CALL,
CHECK_FOR_CALL,
ACCEPT_CALL,
DENY_CALL,
DENY_INVITE,
INVITE_TO_JOIN,
INVITE_A_CALL,
JOIN_CALL,
LEAVE_CALL
} from '../frontend/src/Metamaps/Realtime/events'
const { mapRoom, userMapRoom } = require('./rooms')
module.exports = function (io, state) {
io.on('connection', function (socket) {
socket.on(CHECK_FOR_CALL, function (data) {
var callInProgress = Object.keys(io.nsps['/'].adapter.rooms[data.room] || {}).length
if (callInProgress) socket.emit(CALL_IN_PROGRESS)
})
socket.on(INVITE_A_CALL, function (data) {
socket.broadcast.in(userMapRoom(data.invited, data.mapid)).emit(INVITED_TO_CALL, data.inviter)
})
socket.on(INVITE_TO_JOIN, function (data) {
socket.broadcast.in(userMapRoom(data.invited, data.mapid)).emit(INVITED_TO_JOIN, data.inviter)
})
socket.on(ACCEPT_CALL, function (data) {
socket.broadcast.in(userMapRoom(data.inviter, data.mapid)).emit(CALL_ACCEPTED, data.invited)
socket.broadcast.in(mapRoom(data.mapid)).emit(CALL_STARTED)
})
socket.on(DENY_CALL, function (data) {
socket.broadcast.in(userMapRoom(data.inviter, data.mapid)).emit(CALL_DENIED, data.invited)
})
socket.on(DENY_INVITE, function (data) {
socket.broadcast.in(userMapRoom(data.inviter, data.mapid)).emit(INVITE_DENIED, data.invited)
})
socket.on(JOIN_CALL, function (data) {
socket.broadcast.in(mapRoom(data.mapid)).emit(MAPPER_JOINED_CALL, data.id)
})
socket.on(LEAVE_CALL, function (data) {
socket.broadcast.in(mapRoom(data.mapid)).emit(MAPPER_LEFT_CALL, data.id)
})
})
}

115
realtime/map.js Normal file
View file

@ -0,0 +1,115 @@
import {
MAPPER_LIST_UPDATED,
NEW_MAPPER,
LOST_MAPPER,
MESSAGE_CREATED,
TOPIC_DRAGGED,
TOPIC_CREATED,
TOPIC_REMOVED,
SYNAPSE_CREATED,
SYNAPSE_REMOVED,
PEER_COORDS_UPDATED,
JOIN_MAP,
LEAVE_MAP,
SEND_MAPPER_INFO,
SEND_COORDS,
CREATE_MESSAGE,
DRAG_TOPIC,
CREATE_TOPIC,
REMOVE_TOPIC,
CREATE_SYNAPSE,
REMOVE_SYNAPSE
} from '../frontend/src/Metamaps/Realtime/events'
const { mapRoom, userMapRoom } = require('./rooms')
module.exports = function (io, state) {
io.on('connection', function (socket) {
// this will ping everyone on a map that there's a person just joined the map
socket.on(JOIN_MAP, function (data) {
socket.mapid = data.mapid
socket.userid = data.userid
socket.username = data.username
socket.userimage = data.userimage
var newUser = {
userid: data.userid,
username: data.username,
userimage: data.userimage
}
socket.join(mapRoom(data.mapid))
socket.join(userMapRoom(data.userid, data.mapid))
socket.broadcast.in(mapRoom(data.mapid)).emit(NEW_MAPPER, newUser)
})
const leaveMap = () => {
var data = {
username: socket.username,
userid: socket.userid
}
socket.leave(mapRoom(socket.mapid))
socket.leave(userMapRoom(socket.userid, socket.mapid))
socket.broadcast.in(mapRoom(socket.mapid)).emit(LOST_MAPPER, data)
socket.mapid = null
}
socket.on(LEAVE_MAP, leaveMap)
socket.on('disconnect', leaveMap)
// this will ping a new person with awareness of who's already on the map
socket.on(SEND_MAPPER_INFO, function (data) {
var existingUser = {
userid: data.userid,
username: data.username,
userinconversation: data.userinconversation,
userimage: data.userimage
}
socket.broadcast.in(userMapRoom(data.userToNotify, data.mapid)).emit(MAPPER_LIST_UPDATED, existingUser)
})
socket.on(SEND_COORDS, function (data) {
var peer = {
userid: data.userid,
usercoords: data.usercoords
}
socket.broadcast.in(mapRoom(data.mapid)).emit(PEER_COORDS_UPDATED, peer)
})
socket.on(CREATE_MESSAGE, function (data) {
var mapId = data.mapid
delete data.mapid
socket.broadcast.in(mapRoom(mapId)).emit(MESSAGE_CREATED, data)
})
socket.on(DRAG_TOPIC, function (data) {
var mapId = data.mapid
delete data.mapid
socket.broadcast.in(mapRoom(mapId)).emit(TOPIC_DRAGGED, data)
})
socket.on(CREATE_TOPIC, function (data) {
var mapId = data.mapid
delete data.mapid
socket.broadcast.in(mapRoom(mapId)).emit(TOPIC_CREATED, data)
})
socket.on(REMOVE_TOPIC, function (data) {
var mapId = data.mapid
delete data.mapid
socket.broadcast.in(mapRoom(mapId)).emit(TOPIC_REMOVED, data)
})
socket.on(CREATE_SYNAPSE, function (data) {
var mapId = data.mapid
delete data.mapid
socket.broadcast.in(mapRoom(mapId)).emit(SYNAPSE_CREATED, data)
})
socket.on(REMOVE_SYNAPSE, function (data) {
var mapId = data.mapid
delete data.mapid
socket.broadcast.in(mapRoom(mapId)).emit(SYNAPSE_REMOVED, data)
})
})
}

View file

@ -1,267 +1,18 @@
var
io = require('socket.io').listen(5001),
signalServer = require('./signal'),
io = require('socket.io')(),
signalling = require('./signal'),
junto = require('./junto'),
map = require('./map'),
global = require('./global'),
stunservers = [{"url": "stun:stun.l.google.com:19302"}]
import {
// server sendable, client receivable
INVITED_TO_CALL,
INVITED_TO_JOIN,
CALL_ACCEPTED,
CALL_DENIED,
INVITE_DENIED,
CALL_IN_PROGRESS,
CALL_STARTED,
MAPPER_JOINED_CALL,
MAPPER_LEFT_CALL,
MAPPER_LIST_UPDATED,
NEW_MAPPER,
LOST_MAPPER,
MESSAGE_CREATED,
TOPIC_DRAGGED,
TOPIC_CREATED,
TOPIC_UPDATED,
TOPIC_REMOVED,
TOPIC_DELETED,
SYNAPSE_CREATED,
SYNAPSE_UPDATED,
SYNAPSE_REMOVED,
SYNAPSE_DELETED,
PEER_COORDS_UPDATED,
LIVE_MAPS_RECEIVED,
MAP_WENT_LIVE,
MAP_CEASED_LIVE,
MAP_UPDATED,
// server receivable, client sendable
REQUEST_LIVE_MAPS,
JOIN_MAP,
LEAVE_MAP,
CHECK_FOR_CALL,
ACCEPT_CALL,
DENY_CALL,
DENY_INVITE,
INVITE_TO_JOIN,
INVITE_A_CALL,
JOIN_CALL,
LEAVE_CALL,
REQUEST_MAPPER_INFO,
SEND_MAPPER_INFO,
SEND_COORDS,
CREATE_MESSAGE,
DRAG_TOPIC,
CREATE_TOPIC,
UPDATE_TOPIC,
REMOVE_TOPIC,
DELETE_TOPIC,
CREATE_SYNAPSE,
UPDATE_SYNAPSE,
REMOVE_SYNAPSE,
DELETE_SYNAPSE,
UPDATE_MAP
} from '../frontend/src/Metamaps/Realtime/events'
io.set('log', false)
function start() {
var livemaps = {}
signalServer(io, stunservers)
io.on('connection', function (socket) {
socket.on(REQUEST_LIVE_MAPS, function (activeUser) {
//constrain response to maps visible to user
var maps = Object.keys(livemaps).map(function(key) { return livemaps[key] })
socket.emit(LIVE_MAPS_RECEIVED, maps)
})
// this will ping a new person with awareness of who's already on the map
socket.on(SEND_MAPPER_INFO, function (data) {
var existingUser = {
userid: data.userid,
username: data.username,
userrealtime: data.userrealtime,
userinconversation: data.userinconversation,
userimage: data.userimage
}
//socket.broadcast.emit(data.userToNotify + '-' + data.mapid + '-UpdateMapperList', existingUser)
socket.broadcast.emit(MAPPER_LIST_UPDATED, existingUser)
})
// as a new mapper check whether there's a call in progress to join
socket.on(CHECK_FOR_CALL, function (data) {
var socketsInRoom = io.sockets.clients(data.room)
//if (socketsInRoom.length) socket.emit('maps-' + data.mapid + '-callInProgress')
if (socketsInRoom.length) socket.emit(CALL_IN_PROGRESS)
})
// send the invitation to start a call
socket.on(INVITE_A_CALL, function (data) {
//socket.broadcast.emit(data.invited + '-' + data.mapid + '-invitedToCall', data.inviter)
socket.broadcast.emit(INVITED_TO_CALL, data.inviter)
})
// send an invitation to join a call in progress
socket.on(INVITE_TO_JOIN, function (data) {
//socket.broadcast.emit(data.invited + '-' + data.mapid + '-invitedToJoin', data.inviter)
socket.broadcast.emit(INVITED_TO_JOIN, data.inviter)
})
// send response back to the inviter
socket.on(ACCEPT_CALL, function (data) {
//socket.broadcast.emit(data.inviter + '-' + data.mapid + '-callAccepted', data.invited)
//socket.broadcast.emit('maps-' + data.mapid + '-callStarting')
socket.broadcast.emit(CALL_ACCEPTED, data.invited)
socket.broadcast.emit(CALL_STARTED)
})
socket.on(DENY_CALL, function (data) {
//socket.broadcast.emit(data.inviter + '-' + data.mapid + '-callDenied', data.invited)
socket.broadcast.emit(CALL_DENIED, data.invited)
})
socket.on(DENY_INVITE, function (data) {
//socket.broadcast.emit(data.inviter + '-' + data.mapid + '-inviteDenied', data.invited)
socket.broadcast.emit(INVITE_DENIED, data.invited)
})
socket.on(JOIN_CALL, function (data) {
//socket.broadcast.emit('maps-' + data.mapid + '-mapperJoinedCall', data.id)
socket.broadcast.emit(MAPPER_JOINED_CALL, data.id)
})
socket.on(LEAVE_CALL, function (data) {
//socket.broadcast.emit('maps-' + data.mapid + '-mapperLeftCall', data.id)
socket.broadcast.emit(MAPPER_LEFT_CALL, data.id)
})
// this will ping everyone on a map that there's a person just joined the map
socket.on(JOIN_MAP, function (data) {
if (!livemaps[data.mapid]) {
livemaps[data.mapid] = data.map // { name: '', desc: '', numTopics: '' }
livemaps[data.mapid].mapper_count = 1
io.sockets.emit(MAP_WENT_LIVE, livemaps[data.mapid])
}
else {
livemaps[data.mapid].mapper_count++
}
socket.set('mapid', data.mapid)
socket.set('userid', data.userid)
socket.set('username', data.username)
var newUser = {
userid: data.userid,
username: data.username,
userimage: data.userimage
}
//socket.broadcast.emit('maps-' + data.mapid + '-newmapper', newUser)
socket.broadcast.emit(NEW_MAPPER, newUser)
})
var end = function () {
var socketUserName, socketUserID
socket.get('userid', function (err, id) {
socketUserID = id
})
socket.get('username', function (err, name) {
socketUserName = name
})
var data = {
username: socketUserName,
userid: socketUserID
}
socket.get('mapid', function (err, mapid) {
if (livemaps[mapid] && livemaps[mapid].mapper_count == 1) {
delete livemaps[mapid]
io.sockets.emit(MAP_CEASED_LIVE, { id: mapid })
}
else if (livemaps[mapid]) {
livemaps[mapid].mapper_count--
}
// scope by map
socket.broadcast.emit(LOST_MAPPER, data)
})
}
// this will ping everyone on a map that there's a person just left the map
socket.on('disconnect', end)
socket.on(LEAVE_MAP, end)
socket.on(SEND_COORDS, function (data) {
var peer = {
userid: data.userid,
usercoords: data.usercoords
}
//socket.broadcast.emit('maps-' + data.mapid + '-updatePeerCoords', peer)
socket.broadcast.emit(PEER_COORDS_UPDATED, peer)
})
socket.on(DRAG_TOPIC, function (data) {
var mapId = data.mapid
delete data.mapid
//socket.broadcast.emit('maps-' + mapId + '-topicDrag', data)
socket.broadcast.emit(TOPIC_DRAGGED, data)
})
socket.on(CREATE_MESSAGE, function (data) {
var mapId = data.mapid
delete data.mapid
//socket.broadcast.emit('maps-' + mapId + '-newMessage', data)
socket.broadcast.emit(MESSAGE_CREATED, data)
})
socket.on(CREATE_TOPIC, function (data) {
var mapId = data.mapid
delete data.mapid
//socket.broadcast.emit('maps-' + mapId + '-newTopic', data)
socket.broadcast.emit(TOPIC_CREATED, data)
})
socket.on(UPDATE_TOPIC, function (data) {
socket.broadcast.emit(TOPIC_UPDATED, data)
})
socket.on(REMOVE_TOPIC, function (data) {
var mapId = data.mapid
delete data.mapid
//socket.broadcast.emit('maps-' + mapId + '-removeTopic', data)
socket.broadcast.emit(TOPIC_REMOVED, data)
})
socket.on(DELETE_TOPIC, function (data) {
socket.broadcast.emit(TOPIC_DELETED, data)
})
socket.on(CREATE_SYNAPSE, function (data) {
var mapId = data.mapid
delete data.mapid
//socket.broadcast.emit('maps-' + mapId + '-newSynapse', data)
socket.broadcast.emit(SYNAPSE_CREATED, data)
})
socket.on(UPDATE_SYNAPSE, function (data) {
socket.broadcast.emit(SYNAPSE_UPDATED, data)
})
socket.on(REMOVE_SYNAPSE, function (data) {
var mapId = data.mapid
delete data.mapid
//socket.broadcast.emit('maps-' + mapId + '-removeSynapse', data)
socket.broadcast.emit(SYNAPSE_REMOVED, data)
})
socket.on(DELETE_SYNAPSE, function (data) {
//socket.broadcast.emit('deleteSynapseFromServer', data)
socket.broadcast.emit(SYNAPSE_DELETED, data)
})
socket.on(UPDATE_MAP, function (data) {
socket.broadcast.emit(MAP_UPDATED, data)
})
})
var state = {
connectedPeople: {},
liveMaps: {}
}
signalling(io, stunservers, state)
junto(io, state)
map(io, state)
global(io, state)
io.listen(5001)
start()

6
realtime/rooms.js Normal file
View file

@ -0,0 +1,6 @@
module.exports = {
mapRoom: mapId => `maps/${mapId}`,
userMapRoom: (mapperId, mapId) => `mappers/${mapperId}/maps/${mapId}`,
userRoom: mapperId => `mappers/${mapperId}`
}

View file

@ -1,111 +1,151 @@
var uuid = require('node-uuid');
var uuid = require('node-uuid')
module.exports = function(io, stunservers) {
// based off of https://github.com/andyet/signalmaster
// since it was updated to socket.io 1.3.7
var
activePeople = 0;
function describeRoom(name) {
var clients = io.sockets.clients(name);
var result = {
clients: {}
};
clients.forEach(function (client) {
result.clients[client.id] = client.resources;
});
return result;
function safeCb(cb) {
if (typeof cb === 'function') {
return cb;
} else {
return function () {};
}
}
function safeCb(cb) {
if (typeof cb === 'function') {
return cb;
} else {
return function () {};
}
}
module.exports = function(io, stunservers, state) {
io.sockets.on('connection', function (client) {
activePeople += 1;
client.resources = {
io.on('connection', function (socket) {
socket.resources = {
screen: false,
video: true,
audio: false
};
}
// pass a message to another id
client.on('message', function (details) {
if (!details) return;
socket.on('message', function (details) {
if (!details) return
var otherClient = io.sockets.sockets[details.to];
if (!otherClient) return;
var otherClient = io.to(details.to)
if (!otherClient) return
details.from = client.id;
otherClient.emit('message', details);
});
details.from = socket.id
otherClient.emit('message', details)
})
client.on('shareScreen', function () {
client.resources.screen = true;
});
socket.on('shareScreen', function () {
socket.resources.screen = true
})
client.on('unshareScreen', function (type) {
client.resources.screen = false;
removeFeed('screen');
});
socket.on('unshareScreen', function (type) {
socket.resources.screen = false
removeFeed('screen')
})
client.on('join', join);
socket.on('join', join)
function removeFeed(type) {
if (client.room) {
io.sockets.in(client.room).emit('remove', {
id: client.id,
if (socket.room) {
io.sockets.in(socket.room).emit('remove', {
id: socket.id,
type: type
});
})
if (!type) {
client.leave(client.room);
client.room = undefined;
socket.leave(socket.room)
socket.room = undefined
}
}
}
function join(name, cb) {
// sanity check
if (typeof name !== 'string') return;
if (typeof name !== 'string') return
/*
// check if maximum number of sockets reached
if (config.rooms && config.rooms.maxClients > 0 &&
socketsInRoom(name) >= config.rooms.maxClients) {
safeCb(cb)('full')
return
}*/
// leave any existing rooms
removeFeed();
safeCb(cb)(null, describeRoom(name));
client.join(name);
client.room = name;
removeFeed()
safeCb(cb)(null, describeRoom(name))
socket.join(name)
socket.room = name
}
// we don't want to pass "leave" directly because the
// event type string of "socket end" gets passed too.
client.on('disconnect', function () {
removeFeed();
activePeople -= 1;
});
client.on('leave', function () {
removeFeed();
});
socket.on('disconnect', function () {
removeFeed()
})
socket.on('leave', function () {
removeFeed()
})
client.on('create', function (name, cb) {
socket.on('create', function (name, cb) {
if (arguments.length == 2) {
cb = (typeof cb == 'function') ? cb : function () {};
name = name || uuid();
cb = (typeof cb == 'function') ? cb : function () {}
name = name || uuid()
} else {
cb = name;
name = uuid();
cb = name
name = uuid()
}
// check if exists
if (io.sockets.clients(name).length) {
safeCb(cb)('taken');
var room = io.nsps['/'].adapter.rooms[name]
if (room && room.length) {
safeCb(cb)('taken')
} else {
join(name);
safeCb(cb)(null, name);
join(name)
safeCb(cb)(null, name)
}
});
})
// tell client about stun and turn servers and generate nonces
client.emit('stunservers', stunservers || []);
});
};
// support for logging full webrtc traces to stdout
// useful for large-scale error monitoring
socket.on('trace', function (data) {
console.log('trace', JSON.stringify(
[data.type, data.session, data.prefix, data.peer, data.time, data.value]
))
})
/*
// tell socket about stun and turn servers and generate nonces
socket.emit('stunservers', config.stunservers || [])
// create shared secret nonces for TURN authentication
// the process is described in draft-uberti-behave-turn-rest
var credentials = []
// allow selectively vending turn credentials based on origin.
var origin = socket.handshake.headers.origin
if (!config.turnorigins || config.turnorigins.indexOf(origin) !== -1) {
config.turnservers.forEach(function (server) {
var hmac = crypto.createHmac('sha1', server.secret)
// default to 86400 seconds timeout unless specified
var username = Math.floor(new Date().getTime() / 1000) + (server.expiry || 86400) + ""
hmac.update(username)
credentials.push({
username: username,
credential: hmac.digest('base64'),
urls: server.urls || server.url
})
})
}
socket.emit('turnservers', credentials)
*/
})
function describeRoom(name) {
var adapter = io.nsps['/'].adapter
var sockets = adapter.rooms[name] || {}
var result = {
clients: {}
}
Object.keys(sockets).forEach(function (id) {
result.clients[id] = adapter.nsp.connected[id].resources
})
return result
}
function socketsInRoom(name) {
return io.sockets.sockets(name).length
}
}