小编典典

RequireJS中的动态require,是否出现“尚未为上下文加载模块名称”错误?

javascript

有没有一种方法可以定义一个在RequireJS中“动态”加载其他模块的模块?如果是,优化器(r.js)如何理解如何/何时必须包含一个模块?

例如,让dynModules一个定义名称/路径对的模块:

define([], function () {
    return ['moduleA', 'moduleB']; // Array of module names
});

另一个模块将基于该阵列动态加载模块。这将 不起作用

define(['dyn_modules'], function (dynModules) {
    for(name in dynModules) {   
        var module = require(path); // Call RequireJS require
    }

    // ...
});

… 给我:

未捕获的错误:尚未为上下文_加载模块名称“ moduleA”。使用require([])
http://requirejs.org/docs/errors.html#notloaded

我可以 解决错误 ,但是它不再是“动态的”:

define(['dyn_modules', 'moduleA', 'moduleB'], function (dynModules) {
    for(name in dynModules) {   
        var module = require(path); // Call RequireJS require
    }

    // ...
});

阅读 487

收藏
2020-05-01

共1个答案

小编典典

该限制与简化的CommonJS语法和常规回调语法有关:

由于下载模块的时间未知,因此加载模块本质上是一个异步过程。但是,在服务器端CommonJS规范的仿真中,RequireJS试图为您提供简化的语法。当您执行以下操作时:

var foomodule = require('foo');
// do something with fooModule

幕后发生的事情是RequireJS正在查看函数代码的主体,并解析出您需要’foo’并在函数执行之前加载它。但是,当变量或除简单字符串以外的任何内容(例如您的示例)…

var module = require(path); // Call RequireJS require

…然后Require无法解析出来并自动将其转换。解决方案是将转换为回调语法。

var moduleName = 'foo';
require([moduleName], function(fooModule){
    // do something with fooModule
})

鉴于以上所述,这是您的第二个示例可能的重写,以使用标准语法:

define(['dyn_modules'], function (dynModules) {
    require(dynModules, function(){
        // use arguments since you don't know how many modules you're getting in the callback
        for (var i = 0; i < arguments.length; i++){
            var mymodule = arguments[i];
            // do something with mymodule...
        }
    });

});

编辑:从您自己的答案,我看到您正在使用下划线/破折号,因此使用_.values_.object可以简化上述遍历参数数组的循环。

2020-05-01