Nodejs聊天室例子代码,运行出错,TypeError: Object #<Socket> has no method 'set'
Nodejs聊天室例子代码,运行出错,TypeError: Object #<Socket> has no method 'set’
var httpd = require(‘http’).createServer(handler); var io = require(‘socket.io’).listen(httpd); var fs = require(‘fs’);
httpd.listen(4000);
function handler(req,res){ fs.readFile(__dirname + ‘/index.html’, function(err,data){ if(err){ res.writeHead(500); return res.end(‘错误读取index.html文件’); } res.writeHead(200); res.end(data); }); }
io.sockets.on(‘connection’,function(socket){ socket.on(‘clientMessage’,function(content){ socket.emit(‘serverMessage’,'You said: ’ + content); socket.get(‘username’,function(err,username){ if(! username){ username = socket.id; } socket.broadcast.emit(‘serverMessage’,username + ’ said: ’ + content); }); });
socket.on('login',function(username){
socket.set('username',username,function(err){
if(err) { throw err;}
socket.emit('serverMessage','Currently logged in as ' + username);
socket.broadcast.emit('serverMessage','User ' + username + 'logged in');
});
});
socket.emit(‘login’);
});
以上代码可运行,一旦输入用户名提示TypeError: Object #<Socket> has no method 'set’报错退出,请问是神马原因?
你遇到的错误 TypeError: Object #<Socket> has no method 'set'
是因为 socket.set
和 socket.get
方法在较新版本的 Socket.IO 中已经被移除。Socket.IO 的 API 发生了一些变化,新的版本使用不同的方法来设置和获取数据。
下面是修改后的代码示例:
var httpd = require('http').createServer(handler);
var io = require('socket.io').listen(httpd);
var fs = require('fs');
httpd.listen(4000);
function handler(req, res) {
fs.readFile(__dirname + '/index.html',
function (err, data) {
if (err) {
res.writeHead(500);
return res.end('错误读取index.html文件');
}
res.writeHead(200);
res.end(data);
});
}
io.sockets.on('connection', function (socket) {
socket.on('clientMessage', function (content) {
socket.emit('serverMessage', 'You said: ' + content);
socket.username = socket.username || socket.id;
socket.broadcast.emit('serverMessage', socket.username + ' said: ' + content);
});
socket.on('login', function (username) {
socket.username = username;
socket.emit('serverMessage', 'Currently logged in as ' + username);
socket.broadcast.emit('serverMessage', 'User ' + username + ' logged in');
});
socket.emit('login');
});
解释
-
删除
socket.set
和socket.get
:- 在新的 Socket.IO 版本中,不再有
socket.set
和socket.get
方法。 - 取而代之的是直接使用 JavaScript 对象属性来存储和检索数据。例如,将用户名存储为
socket.username
。
- 在新的 Socket.IO 版本中,不再有
-
更新登录逻辑:
- 当用户登录时,将用户名存储在
socket.username
属性中,而不是使用socket.set
。 - 这样可以在后续的消息处理中轻松访问用户名。
- 当用户登录时,将用户名存储在
-
广播消息:
- 使用
socket.broadcast.emit
来向其他客户端发送消息。
- 使用
通过这些修改,你的聊天室代码应该可以正常运行,不会再出现 TypeError
错误。
socket.io中的get / set方法在新版本中已经被抛弃了,官方文档中有说的 http://socket.io/docs/migrating-from-0-9/
那用什么方法代替了呢?
你遇到的 TypeError: Object #<Socket> has no method 'set'
错误是因为 socket.set
和 socket.get
方法在较新的 Socket.IO 版本中已被移除。Socket.IO 从 v1.0 开始采用不同的方式来存储和检索用户数据。
你可以使用 socket.handshake.query
或者将数据存储在服务器端的数据结构(如一个全局对象)中来代替。
以下是如何修改你的代码以适应 Socket.IO v4.x 的示例:
const http = require('http').createServer(handler);
const io = require('socket.io')(http);
const fs = require('fs');
http.listen(4000);
function handler(req, res) {
fs.readFile(__dirname + '/index.html', (err, data) => {
if (err) {
res.writeHead(500);
return res.end('错误读取index.html文件');
}
res.writeHead(200);
res.end(data);
});
}
let users = {};
io.on('connection', (socket) => {
socket.on('clientMessage', (content) => {
const username = users[socket.id] || socket.id;
socket.emit('serverMessage', 'You said: ' + content);
socket.broadcast.emit('serverMessage', username + ' said: ' + content);
});
socket.on('login', (username) => {
users[socket.id] = username;
socket.emit('serverMessage', 'Currently logged in as ' + username);
socket.broadcast.emit('serverMessage', 'User ' + username + ' logged in');
});
// 示例登录事件触发
socket.emit('login');
});
在这个修改后的版本中,我使用了一个名为 users
的全局对象来存储每个连接用户的用户名。这样可以避免使用已弃用的 socket.set
和 socket.get
方法。当接收到客户端的消息时,我们检查 users
对象中的用户名,并将其发送给其他客户端。