NodeJS,SocketIO和Express逻辑上下文构建

时间:2014-09-03 03:30:14

标签: javascript node.js sockets express socket.io

我读了很多关于Express / SocketIO的内容并且很疯狂你很少得到其他一些例子而不是" Hello"直接从app.js传输问题是它在现实世界中并没有像那样工作......我实际上迫切需要一个逻辑问题,这个问题似乎远离网络给我的东西,这就是我想要的原因指出这一点,我肯定会问这将是解决方案! :)

我正在重构我的应用程序(因为有许多错误,例如使用全局范围来放置库等);让我们说我有一个基于SocketIO和NodeJS的庞大系统。 app.js中有一个加载器,用于启动套接字系统。

当有人加入应用程序时,它需要()另一个模块:它初始化许多socket.on(),它们被动态加载并转到文件夹中的某些/*_socket.js文件。这些模块中的每个函数都代表一个套接字监听器,然后从前端调用它更容易,可能如下所示:

  // Will call `user_socket.js` and method `try_to_signin(some params)`

  Queries.emit_socket('user.try_to_signin', {some params});

系统本身运作良好。但是有一个问题:将加载所有那些了解前端发送的文件的模块还传输与req / res链接的库(会话,cookie,其他......)并且必须这样做,因为被调用的方法是应用程序的核心,并且经常需要这些库。

在上一个示例中,我们显然需要检查用户是否已经登录。

  // The *_socket.js file looks like this :

  var $h = require(__ROOT__ + '/api/helpers');

  module.exports = function($s, $w) {

    var user_process = require(__ROOT__ + '/api/processes/user_process')($s, $w);

      return {

        my_method_called: function(reference, params, callback) {

          // Stuff using $s, $w, etc.

        }

  }

  // And it's called this way :

  // $s = services (a big object)
  // $w = workers (a big object depending on $s)
  // They are linked with the req/res from the page when they are instantiated

  controller_instance = require('../sockets/'+ controller_name +'_socket')($s, $w);

  // After some processes ...

  socket_io.on(socket_listener, function (datas, callback) {

       // Will call the correct function, etc.

       $w.queries.handle_socket($w, controller_name, method_name, datas);

  });

好消息:基本上,它有效。

坏消息:每次刷新页面时,听众都会加倍,因为它们处于页面加载时调用的循环中。

下面,这应该是一行:

enter image description here

所以我应该将所有socket.on(' connection' ...)的东西放在页面加载之外,这意味着当服务器启动时...是的,但我还需要req / res数据可以加载库,只有在加载页面时我才能获得!

这是一个编程逻辑问题,我知道我做错了什么但我现在不知道该去哪里,我得到了这个基本上"基本上"虽然有效,但在我做这件事的方式上却有点悖论,我无法弄清楚如何解决这个问题......我被困了几个小时。 / p>

如何根据socket.on()调用中的req / res来重构以获取当前库的可能性?有诀窍吗?我是否应该考虑完全改变我的做法?

另外,还有另一种方法可以做我想做的事吗?

谢谢大家!

注意:如果我没有解释清楚或者您想要更多代码,请告诉我:)

编辑 - 解决方案:如上所示,我们可以使用sockets.once();而不是sockets.on(),或者还有那些不太干净的sockets.removeAllListeners()解决方案。

1 个答案:

答案 0 :(得分:3)

尝试以下。

io.sockets.once('connection', function(socket) {
  io.sockets.emit('new-data', {
    channel: 'stdout',
    value: data
 }); 
});

使用一次而不是开启。

此问题与以下链接中的说明类似。

https://stackoverflow.com/questions/25601064/multiple-socket-io-connections-on-page-refresh/25601075#25601075