webpack插件

时间:2015-12-03 11:12:29

标签: plugins webpack

问题:

我正在尝试编写一个webpack插件,将源代码生成器集成到我的webpack构建中。我的完整场景很复杂,因此我将其分解为更简单的问题进展。

第一部分:

我有一个代码生成器,可以从%.js文件生成%.proto文件。例如,对于源文件foo.protobar.proto,我希望我的插件生成以下编译步骤:

                ┌─────────┐
    foo.proto ──┤ codegen ├──> foo.js
                └─────────┘
                ┌─────────┐
    bar.proto ──┤ codegen ├──> bar.js
                └─────────┘

我的意思是在每个%.proto文件中注册此依赖项(用于文件监视)并在编译对象上声明生成的资产(%.js)?

使用require('codegen!foo.proto')可以通过加载程序实现此方案,但是通过第III部分,您将了解为什么加载程序不合适。

我的意图将在make中表达为:

%.js: %.proto
    codegen $^ $@

第二部分:

我的生成器生成的%.js文件现在采用ES6语法,因此需要转换为ES5。我已经配置了babel-loader来编译ES6源代码,如果这有用的话。继续这个例子,步骤将是:

                ┌─────────┐  ┌───────┐
    foo.proto ──┤ codegen ├──┤ babel ├──> foo.js
                └─────────┘  └───────┘
                ┌─────────┐  ┌───────┐
    bar.proto ──┤ codegen ├──┤ babel ├──> bar.js
                └─────────┘  └───────┘

即,我想:

%.js: %.proto
    codegen $^ | babel -o $@

我应该:

  • 在我的插件任务中进行转换,将其隐藏在webpack编译中?
  • 通过在编译对象上创建其他任务来获取webpack来进行转换吗?
  • 以允许webpack通过其已经用于其他来源的适当加载器管道转换它的方式发出生成的js?

第三部分:

我的生成器现在需要一个%.fragment.js的附加输入文件。如何在webpack编译中表达这种依赖关系,以便在%.proto%.fragment.js更改时,文件监视将重建资产?这种多源依赖性是我不认为装载机是合适的方向的原因。

                  ┌─────────┐  ┌───────┐
      foo.proto ──┤ codegen ├──┤ babel ├──> foo.js
foo.fragment.js ──┤         │  │       │
                  └─────────┘  └───────┘
                  ┌─────────┐  ┌───────┐
      bar.proto ──┤ codegen ├──┤ babel ├──> bar.js
bar.fragment.js ──┤         │  │       │
                  └─────────┘  └───────┘

我的意图是:

%.js: %.proto %.fragment.js
    codegen $^ | babel -o $@

this post中,我看到了#34;儿童编辑"。是否有任何webpack文档说明它们是什么或者它们打算如何使用?

或者,这种情况不是webpack打算支持的,即使是通过自定义插件吗?

1 个答案:

答案 0 :(得分:0)

您的问题可以通过装载机解决。我建议您在上班前阅读guidelines

首先是pr [loader] do only a single task。因此,您的原型文件加载器只会生成ES6 js文件。

问:我的意思是在每个%.proto文件上注册此依赖项(用于文件监视)并在编译对象上声明生成的资产(%。js)?

答:您应该以通用方式(如您所述)要求您的原型文件:

require("foo.proto");

并使用emitFile函数生成其他资源:

emitFile(name: string, content: Buffer|String, sourceMap: {...})

问:我是否应该以允许webpack通过适当的加载器管道将其转换为已经用于其他源的方式发出生成的js?

答:是的,你的加载器必须只做一个任务:从proto文件生成ES6 js文件。然后生成的文件将传递给babel:

{test: /\.proto$/, loader: 'babel-loader!proto-loader'}

问:我的生成器现在需要一个%.fragment.js的额外输入文件。如何在webpack编译中表达这种依赖性,以便在更改%.proto或%.fragment.js时,文件监视将重建资产?

答:您必须mark dependencies使用addDependency功能(例如来自文档):

// Loader adding a header
var path = require("path");
module.exports = function(source) {
    this.cacheable();
    var callback = this.async();
    var headerPath = path.resolve("header.js");
    this.addDependency(headerPath);
    fs.readFile(headerPath, "utf-8", function(err, header) {
        if(err) return callback(err);
        callback(null, header + "\n" + source);
    });
};