webpack自定义loader

76 阅读2分钟

webpack是一个打包模块JavaScript的工具,从入口模块出发,识别出源码中的模块化导入语句,递归地找出入口文件的所有依赖,将入口和其所有依赖打包到一个单独的文件中。

什么是loader

webpack是基于node的模块打包工具,它默认只会处理JS和JSON模块,对于其他格式的模块如CSS、IMG等,就不知道如何处理了。这时候需要定义响应的loader,告诉webpack如何处理。loader相当于一个编译器,将源文件经过转化后输出能被webpack处理的新内容,并且一个文件还可以链式的多次被翻译。

loader的职责

  • 职责单一:每个loader只能做一件事
  • 链式调用:第一个loader接收到的是源文件的内容,后续loader都是接收到的上一个loader返回的处理结果,webpack会按顺序链式调用每个loader
  • 统一原则:遵循webpack制定的设计规则和结构,输入和输出均为字符串,各个loader完全独立,即插即用
  • 模块化:保证loader是模块化的。loader生成模块需要遵循和普通模块一样的设计原则
  • 无状态:在多次模块的转化间,我们不应该在loader中保留状态。每个loader运行时应确保与其他编译好的模块保持独立,同样也应该与前几个loader对相同的模块的编译结果保持独立。

实现loader

一个loader就是一个Node.js模块,这个模块需要导出一个函数,这个导出函数的工作就是获得处理前的源内容,对源内容进行处理后,返回处理后的内容

loader“模版”

module.exports = function(source) {
    // source 为 compiler 传递给 loader 的一个文件的源内容
    // 返回处理后的内容
    return source
}

注意:loader中导出的函数不能是箭头函数,原因是webpack为 loader 提供了API都绑定在this对象上

loader返回值

方式一 return

module.exports = function(source) {
    // 处理
    const content = source.replace('el-', 'my-')
    // 返回
    return source
}

方式二 this.callback()

module.exports = function(source) {
    // 处理
    const content = source.replace('el-', 'my-')
    // 返回
    this.callback(null, content)
    return
}

this.callback的详细用法

this.callback(
    // 当无法转换源内容,返回一个Error
    err: Error | null,
    // 源内容转换后的内容
    content: string | Buffer,
    // 用于把转换后的内容得出原内容的Source Map,方便调试
    sourceMap?: sourceMap,
    // 如果转换为原内容生成AST语法树,可以把AST返回
    abstractSyntaxTree?: AST
)

参考文章juejin.cn/post/689164…

案例git github.com/web-ljc/web…