commit
9cb9531b8e
@ -1,111 +0,0 @@
|
||||
|
||||
|
||||
'use strict';
|
||||
|
||||
/* globals define, app, config, socket, ajaxify */
|
||||
|
||||
define('forum/topic/browsing', function() {
|
||||
|
||||
var Browsing = {};
|
||||
|
||||
Browsing.onUpdateUsersInRoom = function(data) {
|
||||
if (data && data.room.indexOf('topic_' + ajaxify.data.tid) !== -1) {
|
||||
$('[component="topic/browsing/list"]').parent().toggleClass('hidden', !data.users.length);
|
||||
for (var i=0; i<data.users.length; ++i) {
|
||||
addUserIcon(data.users[i]);
|
||||
}
|
||||
|
||||
updateUserCount(data.hidden);
|
||||
}
|
||||
};
|
||||
|
||||
Browsing.onUserEnter = function(data) {
|
||||
var browsingList = $('[component="topic/browsing/list"]');
|
||||
var user = browsingList.find('a[data-uid="' + data.uid + '"]');
|
||||
if (!user.length && browsingList.first().children().length < 10) {
|
||||
addUserIcon(data);
|
||||
} else if (user.length) {
|
||||
user.attr('data-count', parseInt(user.attr('data-count'), 10) + 1);
|
||||
} else {
|
||||
increaseUserCount(1);
|
||||
}
|
||||
Browsing.onUserStatusChange(data);
|
||||
};
|
||||
|
||||
Browsing.onUserLeave = function(uid) {
|
||||
if (app.user.uid === parseInt(uid, 10)) {
|
||||
return;
|
||||
}
|
||||
var browsingList = $('[component="topic/browsing/list"]');
|
||||
var user = browsingList.find('a[data-uid="' + uid + '"]');
|
||||
if (user.length) {
|
||||
var count = Math.max(0, parseInt(user.attr('data-count'), 10) - 1);
|
||||
user.attr('data-count', count);
|
||||
if (count <= 0) {
|
||||
user.parent().remove();
|
||||
if (!browsingList.children(':not(.hidden)').length) {
|
||||
browsingList.parent().addClass('hidden');
|
||||
}
|
||||
}
|
||||
} else {
|
||||
increaseUserCount(-1);
|
||||
}
|
||||
};
|
||||
|
||||
Browsing.onUserStatusChange = function(data) {
|
||||
app.updateUserStatus($('[data-uid="' + data.uid + '"] [component="user/status"]'), data.status);
|
||||
|
||||
updateBrowsingUsers(data);
|
||||
};
|
||||
|
||||
function updateBrowsingUsers(data) {
|
||||
var browsingList = $('[component="topic/browsing/list"]');
|
||||
var user = browsingList.find('a[data-uid="'+ data.uid + '"]');
|
||||
if (user.length) {
|
||||
user.parent().toggleClass('hidden', data.status === 'offline');
|
||||
browsingList.parent().toggleClass('hidden', !browsingList.children(':not(.hidden)').length);
|
||||
}
|
||||
}
|
||||
|
||||
function addUserIcon(user) {
|
||||
if (!user.userslug) {
|
||||
return;
|
||||
}
|
||||
var browsingList = $('[component="topic/browsing/list"]');
|
||||
var userEl = createUserIcon(user.uid, user.picture, user.userslug, user.username, user['icon:bgColor'], user['icon:text']);
|
||||
var isSelf = parseInt(user.uid, 10) === parseInt(app.user.uid, 10);
|
||||
if (isSelf) {
|
||||
browsingList.prepend(userEl);
|
||||
} else {
|
||||
browsingList.append(userEl);
|
||||
}
|
||||
|
||||
browsingList.find('a[data-uid]').tooltip({
|
||||
placement: 'top'
|
||||
});
|
||||
}
|
||||
|
||||
function createUserIcon(uid, picture, userslug, username, iconBg, iconText) {
|
||||
if (!$('[component="topic/browsing/list"]').find('[data-uid="' + uid + '"]').length) {
|
||||
var imgOrIcon = picture ?
|
||||
'<img src="'+ picture +'" />' :
|
||||
'<div class="user-icon" style="background-color: ' + iconBg + ';">' + iconText + '</div>';
|
||||
|
||||
return $('<div class="inline-block"><a title="' + username + '" data-uid="' + uid + '" data-count="1" href="' + config.relative_path + '/user/' + userslug + '">' + imgOrIcon + '</a></div>');
|
||||
}
|
||||
}
|
||||
|
||||
function updateUserCount(count) {
|
||||
count = parseInt(count, 10);
|
||||
if (!count || count < 0) {
|
||||
count = 0;
|
||||
}
|
||||
$('[component="topic/browsing/count"]').text(count).parent().toggleClass('hidden', count === 0);
|
||||
}
|
||||
|
||||
function increaseUserCount(incr) {
|
||||
updateUserCount(parseInt($('[component="topic/browsing/count"]').first().text(), 10) + incr);
|
||||
}
|
||||
|
||||
return Browsing;
|
||||
});
|
@ -0,0 +1,73 @@
|
||||
'use strict';
|
||||
|
||||
|
||||
var validator = require('validator');
|
||||
var topics = require('../../topics');
|
||||
|
||||
var SocketRooms = {};
|
||||
|
||||
SocketRooms.getAll = function(socket, data, callback) {
|
||||
|
||||
var websockets = require('../index');
|
||||
var io = websockets.server;
|
||||
if (!io) {
|
||||
return;
|
||||
}
|
||||
|
||||
var roomClients = io.sockets.adapter.rooms;
|
||||
var socketData = {
|
||||
onlineGuestCount: websockets.getOnlineAnonCount(),
|
||||
onlineRegisteredCount: websockets.getOnlineUserCount(),
|
||||
socketCount: websockets.getSocketCount(),
|
||||
users: {
|
||||
categories: roomClients.categories ? Object.keys(roomClients.categories).length : 0,
|
||||
recent: roomClients.recent_topics ? Object.keys(roomClients.recent_topics).length : 0,
|
||||
unread: roomClients.unread_topics ? Object.keys(roomClients.unread_topics).length: 0,
|
||||
popular: roomClients.popular_topics ? Object.keys(roomClients.popular_topics).length: 0,
|
||||
topics: 0,
|
||||
category: 0
|
||||
},
|
||||
topics: {}
|
||||
};
|
||||
|
||||
var topTenTopics = [],
|
||||
tid;
|
||||
|
||||
for (var room in roomClients) {
|
||||
if (roomClients.hasOwnProperty(room)) {
|
||||
tid = room.match(/^topic_(\d+)/);
|
||||
if (tid) {
|
||||
var length = Object.keys(roomClients[room]).length;
|
||||
socketData.users.topics += length;
|
||||
|
||||
topTenTopics.push({tid: tid[1], count: length});
|
||||
} else if (room.match(/^category/)) {
|
||||
socketData.users.category += Object.keys(roomClients[room]).length;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
topTenTopics = topTenTopics.sort(function(a, b) {
|
||||
return b.count - a.count;
|
||||
}).slice(0, 10);
|
||||
|
||||
var topTenTids = topTenTopics.map(function(topic) {
|
||||
return topic.tid;
|
||||
});
|
||||
|
||||
topics.getTopicsFields(topTenTids, ['title'], function(err, titles) {
|
||||
if (err) {
|
||||
return callback(err);
|
||||
}
|
||||
topTenTopics.forEach(function(topic, index) {
|
||||
socketData.topics[topic.tid] = {
|
||||
value: topic.count || 0,
|
||||
title: validator.escape(titles[index].title)
|
||||
};
|
||||
});
|
||||
|
||||
callback(null, socketData);
|
||||
});
|
||||
};
|
||||
|
||||
module.exports = SocketRooms;
|
@ -1,129 +0,0 @@
|
||||
'use strict';
|
||||
|
||||
|
||||
// Temp solution until
|
||||
// https://github.com/NodeBB/NodeBB/issues/2486
|
||||
// and
|
||||
// https://github.com/Automattic/socket.io/issues/1945
|
||||
// are closed.
|
||||
// Once they are closed switch to .clients() and async calls
|
||||
|
||||
|
||||
var pubsub = require('../pubsub'),
|
||||
async = require('async');
|
||||
|
||||
var rooms = {};
|
||||
|
||||
var clientRooms = {};
|
||||
var roomClients = {};
|
||||
|
||||
rooms.enter = function(socket, room) {
|
||||
socket.join(room);
|
||||
pubsub.publish('socket:join', {id: socket.id, room: room});
|
||||
};
|
||||
|
||||
rooms.leave = function(socket, room) {
|
||||
socket.leave(room);
|
||||
pubsub.publish('socket:leave', {id: socket.id, room: room});
|
||||
};
|
||||
|
||||
rooms.leaveAll = function(socket, roomsToLeave) {
|
||||
roomsToLeave.forEach(function(room) {
|
||||
rooms.leave(socket, room);
|
||||
});
|
||||
};
|
||||
|
||||
rooms.broadcast = function(socket, room, msg, data, callback) {
|
||||
var io = require('./'),
|
||||
socketIds = rooms.clients(room);
|
||||
|
||||
callback = callback || function() {};
|
||||
|
||||
// Filter out socketIds that aren't actually connected
|
||||
socketIds = socketIds.filter(function(id) {
|
||||
return io.server.sockets.connected.hasOwnProperty(id);
|
||||
});
|
||||
|
||||
async.map(socketIds, function(id, next) {
|
||||
var timeout,
|
||||
timeoutPassed = false;
|
||||
|
||||
if (socket.id === id) {
|
||||
return setImmediate(next, null, []);
|
||||
}
|
||||
|
||||
timeout = setTimeout(function() {
|
||||
timeoutPassed = true;
|
||||
next(null, []);
|
||||
}, 500);
|
||||
|
||||
io.server.sockets.connected[id].emit(msg, data || {}, function(err, returnData) {
|
||||
clearTimeout(timeout);
|
||||
if (!timeoutPassed) {
|
||||
next(null, returnData);
|
||||
}
|
||||
});
|
||||
}, callback);
|
||||
};
|
||||
|
||||
pubsub.on('socket:join', onSocketJoin);
|
||||
pubsub.on('socket:leave', onSocketLeave);
|
||||
|
||||
function onSocketJoin(data) {
|
||||
clientRooms[data.id] = clientRooms[data.id] || [];
|
||||
if (clientRooms[data.id].indexOf(data.room) === -1) {
|
||||
clientRooms[data.id].push(data.room);
|
||||
}
|
||||
|
||||
roomClients[data.room] = roomClients[data.room] || [];
|
||||
if (roomClients[data.room].indexOf(data.id) === -1) {
|
||||
roomClients[data.room].push(data.id);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
function onSocketLeave(data) {
|
||||
var index;
|
||||
if (Array.isArray(clientRooms[data.id])) {
|
||||
index = clientRooms[data.id].indexOf(data.room);
|
||||
if (index !== -1) {
|
||||
clientRooms[data.id].splice(index, 1);
|
||||
if (!clientRooms[data.id].length) {
|
||||
delete clientRooms[data.id];
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if (Array.isArray(roomClients[data.room])) {
|
||||
index = roomClients[data.room].indexOf(data.id);
|
||||
if (index !== -1) {
|
||||
roomClients[data.room].splice(index, 1);
|
||||
if (!roomClients[data.room].length) {
|
||||
delete roomClients[data.room];
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
rooms.clients = function(room) {
|
||||
return Array.isArray(roomClients[room]) ? roomClients[room] : [];
|
||||
};
|
||||
|
||||
rooms.clientRooms = function(id) {
|
||||
return Array.isArray(clientRooms[id]) ? clientRooms[id] : [];
|
||||
};
|
||||
|
||||
rooms.socketCount = function() {
|
||||
return Object.keys(clientRooms || {}).length;
|
||||
};
|
||||
|
||||
rooms.roomClients = function() {
|
||||
return roomClients;
|
||||
};
|
||||
|
||||
|
||||
|
||||
|
||||
module.exports = rooms;
|
||||
|
Loading…
Reference in New Issue