webpack扫盲——如何编写一个loader - Go语言中文社区

webpack扫盲——如何编写一个loader


目录

前言

一、关于loader

二、确认需求

三、loader编写

1.初始化

2.loader编写

3.增加可配置化代码

四、代码调试


前言

本文默认读者对前端工程化有一定的认识,对webpack有一定的裂解并且知道怎么使用webpack,本文会一步一步带领读者手动编写一个webpack的loader,以此加深对webpack的理解


一、关于loader

loader是webpack里面一个相当重要的一个组成部分,用于将现有的代码转化成目标代码,最为人所知的就是babel,他能够将es6的代码,转化成大部分浏览器浏览器能够执行的es5代码,接下来,我们尝试着通过自己手动编写一个loader,来看清loader是什么

二、确认需求

首先,我们确认一下我们这个简单的loader能做什么,日常中我们应该会有这样的需求,开发环境和生产环境相同的接口api地址是不同的,运行阶段我们可以通过process.env来区分不同的环境使用不同的链接,那么有没有办法在编译阶段就把这件事给做了呢,我们这个loader就可以实现这个功能

三、loader编写

1.初始化

首先我们新建一个文件夹loader-example,目录结构如下

src/index.js

const content = {{ __path__ }};
console.log(content);
document.getElementsByTagName('body')[0].innerHTML = content

package.json

{
  "name": "loader-example",
  "version": "1.0.0",
  "description": "",
  "main": "index.js",
  "scripts": {
    "build": "webpack",
  },
  "keywords": [],
  "author": "",
  "license": "ISC",
  "dependencies": {
    "html-webpack-plugin": "^4.5.0",
    "loader-utils": "^2.0.0",
    "open": "^7.3.0",
    "path": "^0.12.7",
    "webpack": "^5.7.0"
  },
  "devDependencies": {
    "webpack-cli": "^4.2.0"
  }
}

webpack.config.js

module.exports = {
    mode: 'development', // 先设置为development,不压缩代码,方便调试
    entry: {
        main: './src/index.js'
    },
    output: {
        filename: '[name].js',
        path: path.resolve(__dirname, 'dist'),
    },
}

我们的目标是,写一个loader,在编译阶段,把index.js里面的{{ __path__ }}转化为我们真正需要的路径。所以,执行npm install安装所有依赖,然后npm run build,果不其然,报错了,没有办法处理{{ __path__ }},提示我们可能需要一个loader,接下来我们开始loader的编写

 

2.loader编写

其实loader说白了,就是一个函数,我们所需要做的,就是定义一个函数,然后在webpack.config.js里面正确的引入就可以了,我们在根目录下新增目录loaders和文件replaceLoader.js,文件路径为loaders/replaceLoader.js,我们先来一个最简单的

module.exports = function (source) {
    const result = source.replace("{{ __path__ }}", "测试");
    //this.callback 也是官方提供的API,替代return
    this.callback(null, result);
}
我们导出一个函数,这个函数的入参就是原始js的文本,我们可以对它进行任意的操作,现在我们把它替换成测试两个字,最后切记调用一下this.callback将对应的值返回,只有这样,打包之后的内容才会是新的内容,callback遵循error first原则,第一个参数是报错的值,第二个参数是转化后的结果,然后我们更新一下webpack.config.js,在webpack.config.js里面添加module属性如下
module: {
        rules: [{
            test: /.js$/,
            use: {
                loader: path.resolve(__dirname, './loaders/replaceLoader.js'),
            }
        }]
    },

在module里面将对应的loader引入,再次运行npm run build,观察一下dist文件夹下的main.js,你就会发现,模板代码已经被替换成 测试 这两个字了
但是,如果我们还有更高的追求呢,例如我们希望这个插件能实现可配置化呢
 

3.增加可配置化代码

我们修改index.js如下

const loaderUtils = require('loader-utils');
module.exports = function (source) {
    //拿到options 配置
    const options = loaderUtils.getOptions(this);
    //回头options里面配置个value参数
    const { value } = options;
    //将源文件内容替换成value
    const result = source.replace("{{ __path__ }}", JSON.stringify(value));
    //this.callback 也是官方提供的API,替代return
    this.callback(null, result);
}

 我们引入loader-utils这个工具包,让我们能够获取到webpack.config.js上的配置内容,然后我们更新webpack.config.js的module

 module: {
        rules: [{
            test: /.js$/,
            use: {
                loader: path.resolve(__dirname, './loaders/replaceLoader.js'),
                options: {
                    value: 'http://www.baidu.com' //参数传入到loader里面,方便getOptions接收到
                }
            }
        }]
    },

我们在options里面配置对应的参数,这样我们在loader里面就能够取到参数,至此,我们完成了一个很简单的loader

四、代码调试

对于很简单的loader,我们基本可以不怎么调试直接打包就能看到我们的结果对不对,那么,如果对于一些比较复杂的loader,我们应该怎么在编写的过程中进行调试呢?

我们可以直接用命令开启webpack的调试模式,首先我们在我们想要调试的代码里面打上debugger,然后在命令行中输入如下命令进行打包

node --inspect-brk ./node_modules/webpack/bin/webpack.js

这时我们就可以看到监听已经打开

然后我们可以在chome里面打开下面的地址:chrome://inspect/#devices,就会看到以下界面

猛戳红框里面的文字,就可以愉快的调试了

 

版权声明:本文来源CSDN,感谢博主原创文章,遵循 CC 4.0 by-sa 版权协议,转载请附上原文出处链接和本声明。
原文链接:https://blog.csdn.net/xiaomingelv/article/details/110335929
站方申明:本站部分内容来自社区用户分享,若涉及侵权,请联系站方删除。

0 条评论

请先 登录 后评论

官方社群

GO教程

猜你喜欢