使用WebSockets获取客户端列表

我正在构build一个多用户画板,并有一些问题得到并保持所有当前连接的用户的更新列表。 我试图find最好的方式来通知所有现有客户端的新客户端,并将现有的客户端传递给新连接的客户端。 我试图这样做的原因是,当一个客户端绘制一条线时,所有其他客户端在列表中find该客户端,并将线条坐标添加到相应的数组中。

Server.js

var sys = require("sys"); var ws = require('websocket-server'); var server = ws.createServer({debug: true}); server.addListener("connection", function(conn) { // When a message is received, broadcast it too all the clients // that are currently connected. conn.send('NEW_SERVER_MESSAGE:Welcome!'); conn.send('USER_CONNECTED:' + conn.id); conn.addListener("message", function( msg ){ switch(msg) { case 'GET_ALL_ACTIVE_USERS': server.manager.forEach(function(con) { conn.broadcast('USER_CONNECTED:' + con.id); }); break; case 'UPDATE_CURSOR': conn.broadcast( msg + '_' + conn.id ); break; default: conn.broadcast( msg ); break; } }); conn.addListener('close', function( msg ) { conn.broadcast('USER_DISCONNECTED:' + conn.id); }); }); server.addListener("error", function(){ console.log(Array.prototype.join.call(arguments, ", ")); }); server.addListener("listening", function(){ console.log("Listening for connections..."); }); server.addListener("disconnected", function(conn){ console.log("<"+conn.id+"> disconnected."); }); server.listen(8002);</code> 

我的JSnetworking代码:

 sketchPadNet = function (b,s) { var self = this; this.host = "ws://localhost:8002/server.js"; this.id = null; this.users = []; this.heightOffset = 53; this.scene = s; this.connected = b; var User = function(id) { this.id = id; this.nickname = id; this.lines = []; this.position = ""; }; this.init = function () { try { socket = new WebSocket(self.host); socket.onopen = function (msg) { socket.send('GET_ALL_ACTIVE_USERS'); }; socket.onmessage = function (msg) { var m = msg.data.split(':'); switch(m[0]) { case 'USER_CONNECTED': console.log('USER_CONNECTED'); var u = new User(m[1]); u.lines = []; u.nickname = u.id; self.users.push(u); console.log(self.users.length); console.log(self.users); break; case 'USER_DISCONNECTED': console.log('USER_DISCONNECTED'); for(var i = 0; i < self.users.length; ++i) { console.log(self.users[i]); if(m[1] == self.users[i].id) { self.users.splice(i, 1); } } break; case 'DRAW_LINE': var tmpMsg = m[1].split('_'); var id = tmpMsg[8]; var userIndex = ''; for(var i = 0; i < self.users.length; ++i) { if(self.users[i].id == id) userIndex = i; } var p1 = (self.users[userIndex].lines.length < 1) ? new BLUR.Vertex3(tmpMsg[0], tmpMsg[1], tmpMsg[2]) : self.users[userIndex].lines[self.users[userIndex].lines.length - 1].point2; var p2 = new BLUR.Vertex3(tmpMsg[3], tmpMsg[4], tmpMsg[5]); var line = new BLUR.Line3D(p1, p2, tmpMsg[7]); line.material = tmpMsg[6]; // add the newly created line to the scene. self.scene.addObject(line); self.users[userIndex].lines.push(line); break; case 'UPDATE_CURSOR': for(var i = 0; i < self.scene.objects.length; ++i) { if(self.scene.objects[i].type == 'BLUR.Particle') self.scene.removeObject(scene.objects[i]); } var coords = m[1].split('_'); var id = coords[2]; var userIndex = 0; for(var i = 0; i < self.users.length; ++i) { if(self.users[i].id == id) userIndex = i; } self.users[userIndex].position = new BLUR.Vertex3(coords[0], coords[1], 1); var p = new BLUR.Particle( self.users[userIndex].position, 4 ); p.material = new BLUR.RGBColour(176,23,31,0.3); self.scene.addObject(p); break; case 'RECEIVE_ID': self.id = m[1]; self.connected.nicknameObj.text = self.id; console.log(self.id); break; break; } }; socket.onclose = function (msg) { // feck! self.connected.addServerError('Server disconnected, try refreshing.'); }; } catch (ex) { console.log('EXCEPTION: ' + ex); } }; 

目前,当一个新的客户端连接它发送一条消息,并添加到一个数组,当客户端断开连接。 由于某种原因,虽然这不是保持更新? 例如,当一个客户端绘制一条线时,其他的一些会报告这个错误:

 Uncaught TypeError: Cannot read property 'lines' of undefined 

对不起,如果我在这里令人难以置信的愚蠢,但任何帮助表示赞赏!

干杯:)

我试图通过查看代码,但没有出现错误的行号,反正很难。

我想这是这里的问题:

 conn.send('USER_CONNECTED:' + conn.id); // send the connect message to ONE user conn.broadcast('USER_DISCONNECTED:' + conn.id); // send the disconnect to ALL users 

因此,当用户连接时,您似乎只是错过了广播呼叫。

好的,真正的问题似乎在客户端的'DRAW_LINE' 。 您是否确定要将消息广播给所有用户,而不仅仅是将消息发送回客户端?

错误指向您的客户端代码中的这一行:

 var p1 = (self.users[userIndex].lines.length < 1) ? new BLUR.Vertex3(tmpMsg[0], tmpMsg[1], tmpMsg[2]) : self.users[userIndex].lines[self.users[userIndex].lines.length - 1].point2; 

请提供'DRAW_LINE'的服务器代码。 这个问题肯定会出现在那里,而不是其他问题。

此外, self.users[userIndex]undefined 。 也许那个用户不存在?

为什么你需要这个循环? 为什么不只是:

 if(self.users[id] != undefined) { var p1 = (self.users[id].lines.length < 1) ? new BLUR.Vertex3(tmpMsg[0], tmpMsg[1], tmpMsg[2]) : self.users[id].lines[self.users[id].lines.length - 1].point2; } 

我试图find最好的方式来通知所有现有客户端的新客户端,并将现有的客户端传递给新连接的客户端

我build议你看看socket.io 。 如果浏览器不支持websockets,它可以很容易地做到这一点,并可以回到其他可用的传输。

你可能要考虑使用一个现有的服务器,如房间和用户列表内置的东西作为比较,这里是一个用JavaScript编写的多用户画板教程使用联合服务器:

http://www.unionplatform.com/?page_id=2762

这里是联合服务器logging的协议,其中包括房间和客户join/离开房间的消息系统的描述:

http://unionplatform.com/specs/upc/

可能会给你一些想法。

科林