Клиенты Socket.IO получат офлайн-сообщения при возврате
Окружающая среда:
Nodejs + Socketio
Проблема:
- клиент A и клиент B оба подключаются к серверу;
- клиент B не работает;
- клиент A отправляет сообщение клиенту B (клиент B все еще не работает);
- клиент B снова подключится к серверу;
- [ Проблема] клиент B не может получить сообщение от A;
Код сервера
var clients = {};
io.sockets.on('connection', function (socket) {
socket.on('online', function (data) {
if (!clients[data.username]) {
clients[data.username] = socket;
}
io.sockets.emit('message', data.user + 'online now');
});
socket.on('say', function (data) {
if (data.to == 'all') {
io.sockets.emit('message', data.message);
} else { //to specific client
clients[data.to].emit('message', data.message);
}
});
});
Описание
клиент B, подключенный к серверу в одном месте. В течение периода времени клиента B в автономном режиме клиент отправляет сообщения клиенту B. Затем клиент B снова подключается к серверу в другом месте, а клиенту B необходимо получить это сообщение от клиента A. Как заставить его работать?
Ответы
Ответ 1
Объем кода, который мне пришлось бы написать, был бы довольно большим, чтобы создать решение, если я рассмотрю, какой db и его config и клиент. В основном вы должны сохранять свои сообщения в базе данных. По мере поступления сообщений вам придется писать на ваш объект беседы (или что-то вроде сообщений чата между клиентами).
socket.on('say', function (data) {
// pseudo code to save conversation
// var conversation = db.getConversation();
// conversation.addMessage(data.message);
// conversation.save();
if (data.to == 'all') {
io.sockets.emit('message', data.message);
} else { //to specific client
clients[data.to].emit('message', data.message);
}
});
Затем вам нужно будет получить все сообщения из базы данных при подключении клиента.
socket.on('online', function (data) {
if (!clients[data.username]) {
clients[data.username] = socket;
}
// pseudo code to get messages and display to user on first load
// var conversation = db.getConversation();
// var messages = conversation.getLast10Messages();
// messages.forEach(function(message) {
// clients[data.username].emit('message', message);
// });
io.sockets.emit('message', data.user + 'online now');
});
Ответ 2
используйте очередь сообщений, такую как RabbitMQ. всякий раз, когда сообщение поступает из очереди сокетов в очередь получателя и когда приемник присоединяется, он выберет его из очереди.
Ответ 3
Вы можете указать уникальный идентификатор в качестве имени пользователя для каждого пользователя, сохранить его на стороне сервера или использовать имя пользователя, у вас также есть идентификатор клиента (идентификатор сокета), а затем сохранить их в объекте, теперь для каждого пользователя у вас есть объект, который содержит (имя пользователя или уникальный идентификатор) и идентификатор сокета, теперь легко сохранять сообщения, когда пользователь не в сети, а затем отправлять их пользователю.
Перед отправкой каждого события вы можете выполнить поиск идентификатора сокета в подключенном объекте сокетов для socket.if идентификатор сокета существует, вы можете произвести генерацию, в противном случае у вас все еще есть имя пользователя и вы можете сохранять сообщения в базе данных по имени пользователя.
Помните, что вы должны отправлять информацию об объекте получателя (имя пользователя или уникальный идентификатор, а также идентификатор сокета) при каждом излучении от клиента