在需要其他模块之前等待异步操作

时间:2015-07-07 07:14:35

标签: javascript node.js node-modules

在我的main.js中,我正在异步读取文件。加载文件后,我在GLOBAL命名空间中设置了一些对象,并在我的require d模块中使用它们(使用GLOBAL命名空间或不使用它是一个不同的故事,无论如何我都在使用它)

我的require d模块立即期望该变量在加载时存在。那么如何让它等到main.js中我的文件读取完成?我只是在readFile的回调中需要模块吗?或者有更好的方法吗?

示例:

fs.readFile('./file', function (data) {
    // do something

    GLOBAL.obj = data;
});

require('./module.js');

module.js

obj.someFunction();

2 个答案:

答案 0 :(得分:2)

你不喜欢这种解决方案的直觉是可以理解的。 (你的胃是对的)。正确的清理方法(你应该花时间 - 未来 - 你会感谢你):

  • 浏览十个模块中的每一个
  • 为每个人完成它导出的所有功能
  • 对于每个函数计算出来,它们实际所依赖的全局变量。
  • 将这些作为参数添加到函数中。 如果他们现在采取了很多论点,可以考虑将它们分组到对象中,创建有用的模型。

如果一堆函数都依赖于同一组变量,您还可以考虑创建工厂函数

  • 创建一个函数,将以前的全局变量作为参数,并将所有模块的代码包装到该函数中。

  • 使该功能成为模块的单一导出。它用作工厂函数,并为该模块中的所有其他函数创建上下文。它应该返回之前导出的模块。

实施例

// DB used to be a global
module.exports = function(DB) {
    function getUser(user, cb) {
        DB.get('user', db);
    }
    return {getUser: getUser};
};

然后您可以像这样使用它:

var module = require('module')(DB);
module.getUser(myUser, function(){}};

答案 1 :(得分:1)

是的,只需按照异步编程的规则#1进行操作即可。依赖于回调发生的东西必须在该回调中执行。由于您的require取决于异步中设置的变量,因此您只能在其中使用require

fs.readFile('./file', function (data) {
    // do something

    GLOBAL.obj = data;
    require('./module.js');
});