web-dev-qa-db-fra.com

webSocketServer node.js comment différencier les clients

J'essaie d'utiliser des sockets avec node.js, j'ai réussi mais je ne sais pas comment différencier les clients dans mon code . La partie concernant les sockets est la suivante:

var WebSocketServer = require('ws').Server, 
    wss = new WebSocketServer({port: 8080});
wss.on('connection', function(ws) {
    ws.on('message', function(message) {
        console.log('received: %s', message); 
        ws.send(message);
    });
    ws.send('something');
});

Ce code fonctionne bien avec mon client js.

Mais je voudrais envoyer un message à un utilisateur particulier ou à tous les utilisateurs ayant des sockets ouverts sur mon serveur.

Dans mon cas, j'envoie un message en tant que client et je reçois une réponse, mais les autres utilisateurs ne montrent rien.

Je voudrais par exemple que l'utilisateur1 envoie un message au serveur via webSocket et que j'envoie une notification à l'utilisateur2 qui a son socket ouvert.

45
Ajouve

Vous pouvez simplement attribuer un ID utilisateur à un tableau CLIENTS [], qui contiendra tous les utilisateurs. Vous pouvez directement envoyer un message à tous les utilisateurs comme indiqué ci-dessous:

var WebSocketServer = require('ws').Server,
    wss = new WebSocketServer({port: 8080}),
    CLIENTS=[];

wss.on('connection', function(ws) {
    CLIENTS.Push(ws);
    ws.on('message', function(message) {
        console.log('received: %s', message);
        sendAll(message);
    });
    ws.send("NEW USER JOINED");
});

function sendAll (message) {
    for (var i=0; i<CLIENTS.length; i++) {
        CLIENTS[i].send("Message: " + message);
    }
}
43
Ankit Bisht

Dans nodejs, vous pouvez directement modifier le client ws et ajouter des attributs personnalisés pour chaque client séparément. Vous avez aussi une variable globale wss.clients et vous pouvez l’utiliser n’importe où. Veuillez essayer le code suivant et essayez de vous connecter à au moins deux clients:

var WebSocketServer = require('ws').Server;
var wss = new WebSocketServer({
    server: httpsServer
});


wss.getUniqueID = function () {
    function s4() {
        return Math.floor((1 + Math.random()) * 0x10000).toString(16).substring(1);
    }
    return s4() + s4() + '-' + s4();
};

wss.on('connection', function connection(ws, req) {
    ws.id = wss.getUniqueID();

    wss.clients.forEach(function each(client) {
        console.log('Client.ID: ' + client.id);
    });
});

Vous pouvez également passer des paramètres directement dans l'URL de connexion client: 

https://myhost:8080?myCustomParam=1111&myCustomID=2222

Dans la fonction de connexion, vous pouvez obtenir ces paramètres et les affecter directement à votre client ws:

wss.on('connection', function connection(ws, req) {

    const parameters = url.parse(req.url, true);

    ws.uid = wss.getUniqueID();
    ws.chatRoom = {uid: parameters.query.myCustomID};
    ws.hereMyCustomParameter = parameters.query.myCustomParam;
}
34
Jzapata

Cet extrait de code dans le serveur Worlize m'a vraiment beaucoup aidé. Même si vous utilisez ws, le code devrait être facilement adaptable. J'ai sélectionné les parties importantes ici:

// initialization
var connections = {};
var connectionIDCounter = 0;

// when handling a new connection
connection.id = connectionIDCounter ++;
connections[connection.id] = connection;
// in your case you would rewrite these 2 lines as
ws.id = connectionIDCounter ++;
connections[ws.id] = ws;

// when a connection is closed
delete connections[connection.id];
// in your case you would rewrite this line as
delete connections[ws.id];

Maintenant, vous pouvez facilement créer une fonction broadcast () et sendToConnectionId () comme indiqué dans le code lié.

J'espère que cela pourra aider.

7
H Dog

Cela dépend du Websocket que vous utilisez. Par exemple, le plus rapide, trouvé ici: https://github.com/websockets/ws est capable de faire une diffusion via cette méthode:

var WebSocketServer = require('ws').Server,
   wss = new WebSocketServer({Host:'xxxx',port:xxxx}),
   users = [];
wss.broadcast = function broadcast(data) {
wss.clients.forEach(function each(client) {
  client.send(data);
 });
};

Ensuite, dans votre code, vous pourrez utiliser wss.broadcast (message) pour l’envoyer à tous. Pour envoyer un PM à un utilisateur individuel, procédez comme suit:

(1) Dans le message que j'envoie au serveur, j'inclus un nom d'utilisateur (2) Ensuite, dans onMessage, j'enregistre le websocket dans le tableau avec ce nom d'utilisateur, puis je le récupère plus tard par nom d'utilisateur:

wss.on('connection', function(ws) {

  ws.on('message', function(message) {

      users[message.userName] = ws;

(3) Pour envoyer à un utilisateur particulier, vous pouvez ensuite créer des utilisateurs [Nomutilisateur] .send (message);

7
droid-zilla

vous pouvez utiliser l'en-tête de requête 'sec-websocket-key'

wss.on('connection', (ws, req) => {
  ws.id = req.headers['sec-websocket-key']; 

  //statements...
});
3
Serhat Ates

Vous pouvez vérifier l'objet de connexion. Il comporte une identification intégrée pour chaque client connecté. Vous pouvez le trouver ici:

let id=ws._ultron.id;
console.log(id);
3
rrk jonnapalli

J'utilise fd de l'objet ws. Il devrait être unique par client.

var clientID = ws._socket._handle.fd;

Je reçois un numéro différent lorsque j'ouvre un nouvel onglet de navigateur.

Les premiers avaient 11 ans, les suivants 12.

2
Klaus Hessellund

Une solution possible ici pourrait être d’ajouter l’identifiant deviceId devant l’identifiant de l’utilisateur, nous séparerons donc plusieurs utilisateurs avec le même identifiant utilisateur mais sur des appareils différents.

ws://xxxxxxx:9000/userID/<<deviceId>>

2
cyberrspiritt

Par clients si vous voulez parler des connexions ouvertes, vous pouvez utiliser ws.upgradeReq.headers['sec-websocket-key'] comme identifiant. Et conservez tous les objets socket dans un tableau.

Mais si vous souhaitez identifier votre utilisateur, vous devez ajouter des données spécifiques à l'utilisateur dans l'objet socket.

0
Deepak Chaudhary

Si quelqu'un utilise peut-être koa-websocket library, une instance de WebSocket sur le serveur est attachée à ctx à côté de la demande. Cela facilite grandement la manipulation de wss.clients Set (ensemble de sessions dans ws ). Par exemple, transmettez les paramètres via une URL et ajoutez-les à l'instance Websocket à peu près comme ceci:

const wss = ctx.app.ws.server
const { userId } = ctx.request.query

try{

   ctx.websocket.uid = userId

}catch(err){
    console.log(err)
}
0
Marko Balažic