使用webpack在运行时动态地需要JS文件

sra*_*sra 24 javascript requirejs webpack

我试图将一个库从grunt/requirejs移植到webpack并偶然发现一个问题,这可能是这项努力的破坏者.

我尝试移植的库有一个函数,它可以加载和评估多个模块 - 基于我们从配置文件中获取的文件名 - 到我们的应用程序中.代码看起来像这样(咖啡):

loadModules = (arrayOfFilePaths) ->
  new Promise (resolve) ->
    require arrayOfFilePaths, (ms...) ->
      for module in ms
        module ModuleAPI
      resolve()
Run Code Online (Sandbox Code Playgroud)

require这里需要调用运行时其行为与它requireJS一样.Webpack似乎只关心"构建过程"中发生的事情.

这是webpack从根本上不关心的东西吗?如果是这样,我还可以使用requireJS吗?在运行时动态加载资产的好方法是什么?

编辑:loadModule可以加载模块,这些模块在此库的构建时不存在.它们将由实现我的库的应用程序提供.

sra*_*sra 15

所以我发现我的要求是在运行时加载一些文件,只能在"app-compile-time"上使用,而不能在"库编译时"上使用webpack.

我将更改机制,以便我的库不再需要文件,但需要传递所需的模块.有点告诉我,无论如何,这将是更好的API.

编辑澄清:

基本上,而不是:

# in my library
load = (path_to_file) ->
  (require path_to_file).do_something()

# in my app (using the 'compiled' libary)
cool_library.load("file_that_exists_in_my_app")
Run Code Online (Sandbox Code Playgroud)

我这样做:

# in my library
load = (module) ->
  module.do_something()

# in my app (using the 'compiled' libary)
module = require("file_that_exists_in_my_app")
cool_library.load(module)
Run Code Online (Sandbox Code Playgroud)

第一个代码在require.js中工作,但在webpack中没有.

事后看来,我认为在运行时加载第三方库加载文件是非常错误的.

  • 为什么这个答案被低估?我需要做与此问题的作者完全相同的事情,并且还没有找到方法来执行此操作,上下文仅在构建时存在所需文件时才起作用. (7认同)
  • Gil,请重新考虑你对惊叹号的使用;)`require(pathToFile + fileName)`为你获取文件,如果它在你运行`webpack`时可用.如果它在编译时不可用,但稍后会出现 - 例如当您的库加载到项目中时,这些文件存在 - 那么您就需要重新考虑您的"需求"策略.请再次阅读答案.也许你有不同的问题? (2认同)

Bog*_*luk 9

有一个名为context(http://webpack.github.io/docs/context.html)的概念,它允许制作动态要求.

还有可能定义代码分割点:http://webpack.github.io/docs/code-splitting.html

function loadInContext(filename) { 
    return new Promise(function(resolve){
        require(['./'+filename], resolve);
    })
}

function loadModules(namesInContext){
    return Promise.all(namesInContext.map(loadInContext));
}
Run Code Online (Sandbox Code Playgroud)

并使用如下:

loadModules(arrayOfFiles).then(function(){
    modules.forEach(function(module){
        module(moduleAPI);
    })
});
Run Code Online (Sandbox Code Playgroud)

但可能它不是你需要的 - 你将拥有大量的块而不是一个包含所有必需模块的块,并且它可能不是最佳的..

最好在配置文件中定义模块需求,并将其包含在您的构建中:

// modulesConfig.js
module.exports = [
   require(...),
   ....
]

// run.js
require('modulesConfig').forEach(function(module){
    module(moduleAPI);
})
Run Code Online (Sandbox Code Playgroud)

  • 感谢您的回答.我不能使用上下文,因为似乎那些动态加载的模块需要在构建时出现.我的图书馆不是这种情况.它们只有在应用程序本身构建后才可用,而不是我的库. (6认同)