除非全局声明,否则不能从事件处理函数中的函数更新variables
我有一个nodejs后端应用程序,利用mongoose的数据库连接和查询,在这种情况下,在socket.io,即io.on("connection", [callback])
的事件处理程序中执行
然而,每当我在一个事件处理程序的io.on("connection")
,如socket.on("myEvent", [callback])
运行一个查询时更新后处理程序中的variables – 特别是当它mongoose查询的callback。
在某些情况下,inheritance人和我试图运行的例子:
io.on("connection", function(socket) { var myVar; // declare user within event handler scope socket.on("myEvent", function(m) { var query = m.myQuery; User.findOne({query}, function(err, doc) { if (err) { // error handling } else { myVar = doc; console.log(myVar); // logs whole document as it should } }); socket.on("myOtherEvent", function(m){ console.log(myVar); // undefined!? }); });
我也试着用一个自定义的callback函数来处理这个问题,这个函数运行相同的查询并返回文档,因为我认为这可能是由db查询asynchronous造成的,但是这种方法也不能工作。
另外,我试过在socket.on("myEvent)
方法中使用(显然是臭名昭着的) var that = this
方法,希望能引用原来的callbacksocket.on("myEvent)
。
要么我错过了mongoose的整个点,要么我要疯了; 帮助将不胜感激!
编辑 :如前所述,只要我全局声明myVar
variables得到更新在所述mongoose查询的else
块。 然后我可以通过其他socket.on
处理程序访问它。
我应该声明我的variables在socket.on("connection")
块它保持不变,例如,如果我console.log(myVar)
之后声明myVar = "why isn\'t this working?!"
在socket.on("myOtherEvent")
它实际上logging"why isn't this working?!"
到控制台
编辑2 :这里描述了一个非常类似的问题: Node,Mongoose – 无法在查询callback中访问父级作用域
使用myVar = myVar || {}
的解决scheme 然而myVar = myVar || {}
确实不起作用。
编辑3 :build议,我使用(在这种情况下,ES6)承诺为我的查询,我更新的查询(仍然在socket.on
,只是不显示在这里)看起来像下面的例子,我做了基于它:
User.findOne({query}).exec().then(function(doc) { if (!doc) { myVar = null; // unrelated logger.debug("Couldnt find user!"); // unrelated } else { myVar = doc; logger.debug(doc); // correctly prints the whole document logger.debug(user); // also correctly prints whole document } }).catch(function(err){ logger.error("Error searching for query: " + err);// unrelated });
就现在而言,我应该稍后再尝试访问myVar
(查询完成后,文档被打印到控制台,在else
block内),它仍然会打印出我给它的初始值。 无论是一个布尔还是一个string – 它保持不变。
但是 ,有趣的是,我应该全局声明它,它开始更新variables – 然而,它不是唯一的套接字,这就是为什么这种方法不适用于这个具体问题
最初由@Bergi解决 – 谢谢!
对于任何不了解的新手或者不熟悉的人(就像我一样),无法合并套接字连接:
与此问题具体相关的是,Socket.io创build多个实例/处理程序 – 每个套接字一个,具体的。 这意味着有多个套接字连接将使用所述事件处理程序创build多个实例,这也会导致这些variables的多个实例。
例如,如果你想出于某种原因,也可以使用特定于每个套接字连接的本地作用域variables,这也是非常有用的。
谢谢!