手写一个webpack插件(plugin)

这篇具有很好参考价值的文章主要介绍了手写一个webpack插件(plugin)。希望对大家有所帮助。如果存在错误或未考虑完全的地方,请大家不吝赐教,您也可以点击"举报违法"按钮提交疑问。

熟悉 vue 和 react 的小伙伴们都知道,在执行过程中会有各种生命周期钩子,其实webpack也不例外,在使用webpack的时候,我们有时候需要在 webpack 构建流程中引入自定义的行为,这个时候就可以在 hooks 钩子中添加自己的方法。

创建插件

webpack 加载 webpack.config.js 中所有配置,此时 webpack 创建 compiler 对象,遍历所有 plugins 中插件,调用插件的 apply 方法,执行剩下编译流程(触发各个 hooks 事件),具体使用什么钩子和钩子是同步还是异步,请移步compiler 钩子

  1. 创建一个 JavaScript 命名函数或 JavaScript 类
  2. 在插件函数的 prototype 上定义一个 apply 方法
  3. 绑定到 webpack 自身的事件钩子上
  4. 导出这个JavaScript 命名函数或 JavaScript 类
  5. 在 webpack.config.js 文件中引入并调用方法

自定义 banner-webpack-plugin

自定义 banner-webpack-plugin 插件,该插件会在每一个打包后的 js 、css 文件第一行添加注释,先看效果图。
手写一个webpack插件(plugin)

  • emit 钩子是输出 asset 到 output 目录之前执行
  • 获取即将输出的资源文件:compilation.assets
  • 遍历 assets,只处理js和css资源,其他文件不处理
  • 通过 content = entcompilation.assets[filename].source() 获取原来内容
  • 拼接上注释 content = prefix + content
  • 修改资源的 source 和 size
// plugins/banner-webpack-plugin.js

class BannerWebpackPlugin {
  constructor(options = {}) {
    this.options = options;
  }

  apply(compiler) {
    // 在资源输出之前触发
    compiler.hooks.emit.tap("BannerWebpackPlugin", (compilation) => {
      const extensions = ["css", "js"];
      const prefix = `/*
          * Author: ${this.options.author}
          * Build Time: ${new Date()}
          */
          `;
      // 获取即将输出的资源文件:compilation.assets
      for (const filename in compilation.assets) {
        if (compilation.assets.hasOwnProperty(filename)) {
          // 将文件名进行切割
          const splitted = filename.split(".");
          // 获取文件扩展名
          const extension = splitted[splitted.length - 1];
          // 只处理js和css资源,其他文件不处理
          if (extensions.includes(extension)) {
            const asset = compilation.assets[filename];
            // 获取原来内容
            let content = asset.source();
            // 拼接上注释
            content = prefix + content;
            // 修改资源
            compilation.assets[filename] = {
              // 最终资源输出时,调用source方法,source方法的返回值就是资源的具体内容
              source: () => content,
              // 资源大小
              size: () => content.length,
            };
          }
        }
      }
    });
  }
}
module.exports = BannerWebpackPlugin;
调用 BannerWebpackPlugin
// config/webpack.config.js

// 引入插件
const BannerWebpackPlugin = require('../plugins/banner-webpack-plugin');
module.exports = {
  plugins: [
    // 调用插件
    new BannerWebpackPlugin({
      author: "小小愿望",
    }),
  ],
};

自定义 take-time-webpack-plugin

自定义 take-time-webpack-plugin 插件,该插件输出 “webpack 构建正在启动!”,打包完成后输出 webpack 构建已完成!总耗时 { time } ms,先看效果图。
手写一个webpack插件(plugin)

// plugins/take-time-webpack-plugin.js

// 一个命名的 Javascript 方法 或 JavaScript 类
class TakeTimeWebpackPlugin {
  time = 0;
  // 原型上需要定义 apply 的方法
  apply(compiler) {
    // 生命周期钩子函数,是由 compiler 暴露
    // 通过 compiler 获取 webpack 内部的钩子,获取 Webpack 打包过程中的各个阶段
    compiler.hooks.environment.tap("TakeTimeWebpackPlugin", (compilation) => {
      console.log("\x1B[36m", "webpack 构建正在启动!");
      this.time = new Date().getTime();
    });
    // 通过 compiler 获取 webpack 内部的钩子,获取 Webpack 打包过程中的各个阶段
    compiler.hooks.afterEmit.tapAsync("TakeTimeWebpackPlugin", (compilation, callback) => {
      const nowTime = new Date().getTime();
      this.time = nowTime - this.time;
      const str = `webpack 构建已完成!总耗时 ${this.time} ms`
      console.log("\x1B[32m", str);
      // 分为同步和异步的钩子,异步钩子在功能完成后,必须执行对应的回调
      callback();
    });
  }
}
module.exports = TakeTimeWebpackPlugin;
调用 TakeTimeWebpackPlugin

在 config/webpack.config.js 文件中引入并执行 TakeTimeWebpackPlugin文章来源地址https://www.toymoban.com/news/detail-473451.html

// config/webpack.config.js

// 引入插件
const TakeTimeWebpackPlugin = require('../plugins/take-time-webpack-plugin');
module.exports = {
  plugins: [
    // 调用插件
    new TakeTimeWebpackPlugin(),
  ],
};

到了这里,关于手写一个webpack插件(plugin)的文章就介绍完了。如果您还想了解更多内容,请在右上角搜索TOY模板网以前的文章或继续浏览下面的相关文章,希望大家以后多多支持TOY模板网!

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处: 如若内容造成侵权/违法违规/事实不符,请点击违法举报进行投诉反馈,一经查实,立即删除!

领支付宝红包 赞助服务器费用

相关文章

  • React项目通过webpack-plugin-istanbul生成覆盖率报告

        早期开发前端覆盖率的时候,使用的是Vue项目,对应的插件是babel-plugin-istanbul,后来发现公司产品使用的是React项目,babel-plugin-istanbul插件就不太支持了。在网上搜索了一下,发现一个全新的插件:webpack-plugin-istanbul,针对React项目webpack打包进行覆盖率采集的。 项目gitl

    2024年02月12日
    浏览(31)
  • 第3集丨webpack 江湖 —— 插件(plugin)的安装和使用

    webpack plugins 插件可以完成更多 loader 不能完成的功能。插件( plugin )的使用一般是在 webpack 的配置信息 plugins 选项中指定。 Webpack 本身内置了一些常用的插件,还可以通过 npm 安装第三方插件。 webpack-dev-server 可用于快速开发应用程序。类似于 node.js 阶段用到的 nodemon 工具,每

    2024年02月15日
    浏览(44)
  • 初识webpack(二)解析resolve、插件plugins、dev-server

    目录 (一)webpack的解析(resolve) 1.resovle.alias 2.resolve.extensions 3.resolve.mainFiles (二) plugin插件 1.CleanWebpackPlugin 2.HtmlWebpackPlugin 3.DefinePlugin  (三)webpack-dev-server 1.开启本地服务器 2.HMR模块热替换 3.devServer的更多配置项  解析(Resolve) | webpack 中文文档 | webpack中文文档 | webpack中文网 resolve

    2024年02月19日
    浏览(47)
  • 清理构建目标文件夹的两种方式:webpack配置选项 VS clean-webpack-plugin插件

    92. 清理构建目标文件夹的两种方式:webpack配置选项 VS clean-webpack-plugin插件 在 webpack 中, clean: true 是一项配置选项,而 clean-webpack-plugin 是一个插件。它们的作用是清理(删除)构建目标文件夹中的旧文件。 1. clean: true 配置选项: 在 webpack 的配置文件中,你可以使用 clean 配

    2024年02月11日
    浏览(47)
  • React 通过一个输入内容加入列表案例熟悉 Hook 基本使用

    我们创建一个react项目 在src下创建components文件夹 在下面创建一个index.jsx index.jsx 参考代码如下 首先 我们通过一个比较典型的方法定义了一个用于声明表单元素绑定响应式数据的的函数useInputValue 接收一个参数 用于做响应式数据的默认值 然后暴露他的value 同时 绑定了一个o

    2024年02月09日
    浏览(47)
  • 新安webpack插件后编译报错compiler.plugin is not a function

            安装使用generate-asset-webpack-plugin时报错 TypeError:compiler.plugin is not a function ,网上搜索了一下大概就是webpack5与这些插件不匹配。推荐的方法几乎都是换一个适配的插件版本,但我所需要的这个插件在npm上最近更新时间是7年前💔。等不着作者适配于是决定自己改。

    2023年04月24日
    浏览(42)
  • 手写一个 React 图片预览组件

    原文链接: 手写一个 React 图片预览组件 前几天打算给博客添加一个图片预览的效果,可在网上找了半天也没找到合适的库,于是自己干脆自己手写了个。 最终实现效果如下: 当鼠标点击图片时生成一个半透明遮罩,并添加一个与点击图片位置大小都相同的图片,之后通过

    2024年02月08日
    浏览(39)
  • Flutter笔记:手写并发布一个人机滑动验证码插件

    Flutter笔记 手写一个人机滑块验证码 作者 : 李俊才 (jcLee95):https://blog.csdn.net/qq_28550263 邮箱 : 291148484@163.com 本文地址 :https://blog.csdn.net/qq_28550263/article/details/133529459 写 Flutter 项目时,遇到需要滑块验证码功能。滑块验证码属于人机验证码的一种,看起来像是在一个图片

    2024年02月07日
    浏览(35)
  • webpack打包之 copy-webpack-plugin

    copy-webpack-plugin 打包复制文件插件。 1、什么时候要使用? 在离线应用中,前端所有文件都需在在本地,有些文件(比如iconFont以及一些静态img)需要转为离线文件,这些文件可以直接引用更方便些,这就需要在打包时直接复制到打包文件下。 2、安装依赖 3、配置webpack 4、打包

    2024年02月17日
    浏览(42)
  • 手写webpack的loader

    帮助webpack将不同类型的文件转换为webpack可识别的模块。 pre:前置loader normal:普通loader inline:内联loader post:后置loader 4类loader的执行顺序为pernormalinlinepost 相同优先级的loader执行顺序为:从右到左,从下到上。 例如: 使用Loader 的方式 配置方式:在 webpack.config.js 文件中指定

    2024年01月21日
    浏览(42)

觉得文章有用就打赏一下文章作者

支付宝扫一扫打赏

博客赞助

微信扫一扫打赏

请作者喝杯咖啡吧~博客赞助

支付宝扫一扫领取红包,优惠每天领

二维码1

领取红包

二维码2

领红包