【问题标题】:Node.js and socket.io, Clients not sharing counterNode.js 和 socket.io,客户端不共享计数器
【发布时间】:2013-04-14 00:23:52
【问题描述】:

我正在使用 node.js 和 socket.io,试图让计数程序正常工作。基本上它应该是每次连接的客户端按下按钮时将共享计数器增加 1,并将该数字显示给所有连接的客户端。

我得到的是每个客户都有一个单独的计数器。例如,如果我在一个客户上数到 10,然后去开始数另一个客户,它从 1 开始。如果我回去,第一个客户将从 10 恢复。我已尽力解决此问题,但在涉及 JS 范围问题(我怀疑这是)或套接字时,我不太了解。

var socketio = require('socket.io');
var io;
var count = 1;

exports.listen = function(server){
    io = socketio.listen(server);
    io.set('log level', 1);

    io.sockets.on('connection', function (socket){
        joinRoom(socket, 'Lobby');
        count = handleCounter(socket, count);
    });
};

function handleCounter(socket, count){
    socket.on('endCount', function(){
        io.sockets.emit('endCount', {
            success: true,
            num: count
        });
            count++;
            console.log(count);
    });
    return count;
}

function joinRoom(socket, room){
    socket.join(room);
}

作为说明,我之前只是将代码从 handleCounter 放入 io.sockets.on('connection') 函数时,它可以工作,但我想知道为什么当我尝试像上面的代码一样将它放在外面时它不会工作。

非常感谢任何帮助,谢谢。

【问题讨论】:

标签: javascript node.js scope socket.io


【解决方案1】:

您在handleCounter() 的末尾返回count,但它在异步函数中递增,因此在返回之前它没有递增。

您可以引用在文件顶部声明的count 变量,而不是传递count,它在您的所有闭包中都可用。您也不需要endCount 侦听器和发射器,如果您只想在每次客户端连接时向客户端发送新计数。

var socketio = require('socket.io');
var io;
var count = 1;

exports.listen = function(server){
    io = socketio.listen(server);
    io.set('log level', 1);

    io.sockets.on('connection', function (socket){
        joinRoom(socket, 'Lobby');
        handleCounter();
    });
};

function handleCounter(){
    count++;
    console.log(count);

    io.sockets.emit('count', {
        success: true,
        num: count
    });
}

function joinRoom(socket, room){
    socket.join(room);
}

【讨论】:

  • 这行得通,我想我是想通过传递count 来使事情变得过于复杂。实际上,我曾想过通常只引用count 变量,但我总是担心我没有以“正确”的方式做事并开始编码切线。谢谢。 (另外我在客户端按下按钮时增加计数器,所以这就是我使用 endCount 发射器和监听器的目的)
【解决方案2】:

http://realtimeanswer-5042.usw1.actionbox.io:4000/

简而言之,在连接时发送数据,并在单击按钮时将数据发送给所有客户端。

客户端只有在收到来自服务器的消息时才更新 dom。

我在您的代码中看到的最大问题是您使计数范围复杂化。它是模块范围,可以简单地使用而无需传递它。

服务器:

var app = require('express')()
  , server = require('http').createServer(app)
  , io = require('socket.io').listen(server)
  , count = 0;

var port = 4000;

server.listen(port);

app.get('/', function (req, res) {
  res.sendfile(__dirname + '/index.html');
});

io.set('log level', 1);

io.sockets.on('connection', function (socket) {
  console.log(count);
  socket.emit('count', count);
  socket.on('inc', function () {
    count++;
    console.log('inc', count);
    io.sockets.emit('count', count);
  });
});

客户

<!DOCTYPE html>
<meta charset='utf-8'>
<title>real time fun</title>
<script src="/socket.io/socket.io.js"></script>
<script src="http://code.jquery.com/jquery.js"></script>

<script>
  $(function() {
    var socket = io.connect();

    socket.on('count', function (count) {
      $('#count').text(count);
    });

    $('button').click(function () {
      socket.emit('inc');
    });
  });
</script>
<div id='count'></div>
<button>inc</button>

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 2011-05-21
    • 1970-01-01
    • 2020-04-07
    • 2015-10-21
    • 2016-05-31
    • 1970-01-01
    • 2013-01-28
    • 2019-03-31
    相关资源
    最近更新 更多