Webpack 知识总结

目录

一、对 webpack 的理解 

1、什么是 webpack?

2、webpack 的两大特色

二、webpack 中 loader 的作用是什么,以及常用 loader 有哪些?

1、loader 作用

2、常用的 loader 

三、webpack中常见的Plugin?解决了什么问题?

1、plugin 的作用 

2、常见的 Plugin

四、webpack 的 Loader 和 Plugin 的不同

五、Webpack 构建流程简单说一下

六、使用 webpack 开发时,你用过哪些可以提高效率的插件?

七、source map是什么?生产环境怎么用?

八、模块打包原理知道吗?

九、文件监听原理呢?

十、说一下 Webpack 的热更新原理

十一、如何对 bundle 体积进行监控和分析?

十二、在实际工程中,配置文件上百行乃是常事,如何保证各个loader按照预想方式工作?

十三、如何优化 Webpack 的构建速度?

十四、你刚才也提到了代码分割,那代码分割的本质是什么?有什么意义呢?

十五、webpack解决的问题

十六、webpack的能力


一、对 webpack 的理解 

1、什么是 webpack?

webpack 是目前比较常用的模块打包工具,它能够很好地管理与打包开发中所用到的HTML、 JavaScript 、CSS以及各种静态文件(图片、字体等)。使用 webpack 管理模块依赖,并编译输岀模块所需的静态文件,让开发过程更加高效。

对于不同类型的资源, webpack 有对应的模块加载器。它会分析模块间的依赖关系,最后生成优化且合并后的静态资源。

当 webpack 处理应用程序时,它会在内部构建一个依赖图,此依赖图对应映射到项目所需的每个模块(不再局限js文件),然后形成资源列表,最终打包生成到指定的文件中。

webpack 做的事情,仅仅是分析出各种模块的依赖关系,然后形成资源列表,最终打包生成到指定的文件中。

2、webpack 的两大特色

① 代码切割( code splitting)

 可以将代码切割成不同的块,实现按需加载,缩短了初始化时间;

② 使用 loader 处理各种类型的静态文件,并且支持串行操作 webpack 以 CommonJS 规范来书写代码,但对 AMD/CMD 的支持也很全面,方便对项目进行代码迁移。

webpack 具有 require.js和 browserify的功能,但也有很多自己的新特性:

(1)对 CommonJS、AMD、ES6的语法实现了兼容;

(2)对 JavaScript、CSS、图片等资源文件都支持打包;

(3)串联式模块加载器和插件机制,让其具有更好的灵活性和扩展性,例如提供对CoffeeScript、 EMAScript 6的支持;

(4)有独立的配置文件 webpack.config. js;

(5)可以将代码切割成不同的块,实现按需加载,缩短了初始化时间;

(6)支持 SourceUrls 和 SourceMaps,易于调试;

(7)具有强大的 Plugin接口,大多是内部插件,使用起来比较灵活

(8)使用异步I/O,并具有多级缓存,这使得 webpack 速度很快且在增量编译上更加快。

二、webpack 中 loader 的作用是什么,以及常用 loader 有哪些?

说说webpack中常见的Loader?解决了什么问题?- 题目详情 - 前端面试题宝典

1、loader 作用

① 实现对不同格式文件的处理,比如将 Scss 转换为CSS,或将 TypeScript 转化为Javascript;

② 可以编译文件,从而使其能够添加到依赖关系中。

loader是 webpack 最重要的部分之一。通过使用不同的 loader,我们能够调用外部的脚本或者工具,实现对不同格式文件的处理。loader 需要在 webpack.config.js 里单独用 module 进行配置。

更多背景介绍: 

 在 webpack 内部中,任何文件都是模块,不仅仅只是js文件。默认情况下,在遇到import或者load加载模块的时候,webpack只支持对js文件打包,像csssasspng等这些类型的文件的时候,webpack则无能为力,这时候就需要配置对应的loader进行文件内容的解析。

在加载模块的时候,执行顺序如下:

当 webpack 碰到不识别的模块的时候,webpack 会在配置的中查找该文件解析规则。

关于配置loader的方式有三种:

  • 配置方式(推荐):在 webpack.config.js文件中指定 loader
  • 内联方式:在每个 import 语句中显式指定 loader
  • CLI 方式:在 shell 命令中指定它们

配置方式:

关于 loader的配置,我们是写在 module.rules属性中,属性介绍如下:

  • rules是一个数组的形式,因此我们可以配置很多个 loader

  • 每一个loader对应一个对象的形式,对象属性test 为匹配的规则,一般情况为正则表达式

  • 属性use针对匹配到文件类型,调用对应的 loader 进行处理

代码编写,如下形式:

module.exports = {
  module: {
    rules: [
      {
        test: /\.css$/,
        use: [
          { loader: 'style-loader' },
          {
            loader: 'css-loader',
            options: {
              modules: true
            }
          },
          { loader: 'sass-loader' }
        ]
      }
    ]
  }
};

从上述代码可以看到,在处理css模块的时候,use属性中配置了三个loader分别处理css文件。

因为loader支持链式调用,链中的每个loader会处理之前已处理过的资源,最终变为js代码。顺序为相反的顺序执行,即上述执行方式为sass-loadercss-loaderstyle-loader

同一个任务的 loader 可以同时挂载多个,处理顺序为:从右到左,从下往上

除此之外,loader的特性还有如下:

  • loader 可以是同步的,也可以是异步的
  • loader 运行在 Node.js 中,并且能够执行任何操作
  • 除了常见的通过 package.json 的 main 来将一个 npm 模块导出为 loader,还可以在 module.rules 中使用 loader 字段直接引用一个模块
  • 插件(plugin)可以为 loader 带来更多特性
  • loader 能够产生额外的任意文件

可以通过 loader 的预处理函数,为 JavaScript 生态系统提供更多能力。用户现在可以更加灵活地引入细粒度逻辑,例如:压缩、打包、语言翻译和更多其他特性。

2、常用的 loader 

css-loader:加载 CSS,支持模块化、压缩、文件导入等特性;

style-loader:将 解析后的 css, 用 style 标签挂载到页面的 head 中;

如果只通过css-loader加载文件,这时候页面代码设置的样式并没有生效。原因在于,css-loader只是负责将.css文件进行一个解析,而并不会将解析后的css插入到页面中。如果我们希望再完成插入style的操作,那么我们还需要另外一个loader,就是style-loader

less-loader:  将 LESS 代码转换成CSS

sass-loader:  将 SCSS/SASS 代码转换成CSS

开发中,我们也常常会使用lesssassstylus预处理器编写css样式,使开发效率提高,这里需要使用less-loader、sass-loader

postcss-loader: 扩展 CSS 语法,使用下一代 CSS,可以配合 autoprefixer 插件自动补齐 CSS3 前缀;

raw-loader: 在 webpack中通过 import方式导入文件内容,该loader并不是内置的;

babel-loader:把 ES6 转换成 ES5;

eslint-loader:通过 ESLint 检查 JavaScript 代码;

html-minify-loader: 压缩HTML

image-loader:加载并且压缩图片文件;

file-loader:把文件输出到一个文件夹中,在代码中通过相对 URL 去引用输出的文件 (处理图片和字体);

url-loader:与 file-loader 类似,区别是用户可以设置一个阈值,大于阈值会交给file-loader处理,小于阈值时返回文件 base64 形式编码 (处理图片和字体);

source-map-loader:加载额外的 Source Map 文件,以方便断点调试

三、webpack中常见的Plugin?解决了什么问题?

说说webpack中常见的Plugin?解决了什么问题?- 题目详情 - 前端面试题宝典

1、plugin 的作用 

Plugin是一种计算机应用程序,它和主应用程序互相交互,以提供特定的功能。是一种遵循一定规范的应用程序接口编写出来的程序,只能运行在程序规定的系统下,因为其需要调用原纯净系统提供的函数库或者数据。

webpack中的plugin也是如此,plugin赋予其各种灵活的功能,例如打包优化、资源管理、环境变量注入等,它们会运行在 webpack 的不同阶段(钩子 / 生命周期),贯穿了webpack整个编译周期。

目的在于解决 loader 无法实现的其他事。

配置方式

这里讲述文件的配置方式,一般情况,通过配置文件导出对象中plugins属性传入new实例对象。如下所示:

const HtmlWebpackPlugin = require('html-webpack-plugin'); // 通过 npm 安装
const webpack = require('webpack'); // 访问内置的插件
module.exports = {
  ...
  plugins: [
    new webpack.ProgressPlugin(),
    new HtmlWebpackPlugin({ template: './src/index.html' }),
  ],
};

2、常见的 Plugin

html-webpack-plugin:简化 HTML 文件创建 (依赖于 html-loader);

在打包结束后,⾃动生成⼀个 html 文件,并把打包生成的 js 模块引⼊到该 html 中

mini-css-extract-plugin:分离样式文件,CSS 提取为独立文件,支持按需加载 (替代extract-text-webpack-plugin) 

uglifyjs-webpack-plugin:不支持 ES6 压缩 (Webpack4 以前);

terser-webpack-plugin: 支持压缩 ES6 (Webpack4);

webpack-bundle-analyzer:可视化 webpack 输出文件的体积;

optimize-css-plugin:压缩CSS;

copy-webpack-plugin:复制文件或目录到执行区域;

如 Vue 的打包过程中,如果我们将一些文件放到 public 的目录下,那么这个目录会被复制到 dist 文件夹中 

define-plugin:定义环境变量;允许在编译时创建配置的全局对象; (Webpack4 之后指定 mode 会自动配置)

是一个webpack 内置的插件,不需要安装 

webpack-parallel-uglify-plugin:多核压缩,提高压缩速度;

clean-webpack-plugin: 删除(清理)构建目录;

ignore-plugin:忽略部分文件;

webpack-parallel-uglify-plugin: 多进程执行代码压缩,提升构建速度

四、webpack 的 Loader 和 Plugin 的不同

Loader 直译为"加载器"。Webpack 将一切文件视为模块,但是 webpack 原生是只能解析 js 文件,如果想将其他文件也打包的话,就会用到 loader所以 Loader 的作用是让 webpack 拥有了加载和解析非JavaScript文件 的能力。

Plugin 直译为"插件"。Plugin 可以扩展 webpack 的功能,让 webpack 具有更多的灵活性。 在 Webpack 运行的生命周期中会广播出许多事件,Plugin 可以监听这些事件,在合适的时机通过 Webpack 提供的 API 改变输出结果。

不同的用法:

Loader 在 module.rules 中配置,也就是说他作为模块的解析规则而存在。

类型为数组,每一项都是一个Object,里面描述了对于什么类型的文件(test),使用什么加载(loader) 和使用的参数(options

Plugin 在 plugins中单独配置。

类型为数组,每一项是一个plugin的实例,参数都通过构造函数传入。

五、Webpack 构建流程简单说一下

Webpack 的运行流程是一个串行的过程,从启动到结束会依次执行以下流程:

  • 初始化参数:从配置文件和 Shell 语句中读取与合并参数,得出最终的参数
  • 开始编译:用上一步得到的参数初始化 Compiler 对象,加载所有配置的插件,执行对象的 run 方法开始执行编译
  • 确定入口:根据配置中的 entry 找出所有的入口文件
  • 编译模块:从入口文件出发,调用所有配置的 Loader 对模块进行翻译,再找出该模块依赖的模块,再递归本步骤直到所有入口依赖的文件都经过了本步骤的处理
  • 完成模块编译:在经过第4步使用 Loader 翻译完所有模块后,得到了每个模块被翻译后的最终内容以及它们之间的依赖关系
  • 输出资源:根据入口和模块之间的依赖关系,组装成一个个包含多个模块的 Chunk,再把每个 Chunk 转换成一个单独的文件加入到输出列表,这步是可以修改输出内容的最后机会
  • 输出完成:在确定好输出内容后,根据配置确定输出的路径和文件名,把文件内容写入到文件系统

在以上过程中,Webpack 会在特定的时间点广播出特定的事件,插件在监听到感兴趣的事件后会执行特定的逻辑,并且插件可以调用 Webpack 提供的 API 改变 Webpack 的运行结果。

简单说

  • 初始化:启动构建,读取与合并配置参数,加载 Plugin,实例化 Compiler
  • 编译:从 Entry 出发,针对每个 Module 串行调用对应的 Loader 去翻译文件的内容,再找到该 Module 依赖的 Module,递归地进行编译处理
  • 输出:将编译后的 Module 组合成 Chunk,将 Chunk 转换成文件,输出到文件系统中

六、使用 webpack 开发时,你用过哪些可以提高效率的插件?

  • webpack-dashboard:可以更友好的展示相关打包信息。
  • webpack-merge:提取公共配置,减少重复配置代码
  • speed-measure-webpack-plugin:简称 SMP,分析出 Webpack 打包过程中 Loader 和 Plugin 的耗时,有助于找到构建过程中的性能瓶颈。
  • size-plugin:监控资源体积变化,尽早发现问题
  • HotModuleReplacementPlugin:模块热替换

七、source map是什么?生产环境怎么用?

source map 是将编译、打包、压缩后的代码映射回源代码的过程。打包压缩后的代码不具备良好的可读性,想要调试源码就需要 soucre map。

map文件只要不打开开发者工具,浏览器是不会加载的。

线上环境一般有三种处理方案:

  • hidden-source-map:借助第三方错误监控平台 Sentry 使用
  • nosources-source-map:只会显示具体行数以及查看源代码的错误栈。安全性比 sourcemap 高
  • sourcemap:通过 nginx 设置将 .map 文件只对白名单开放(公司内网)

注意:避免在生产中使用 inline- 和 eval-,因为它们会增加 bundle 体积大小,并降低整体性能。

八、模块打包原理知道吗?

Webpack 实际上为每个模块创造了一个可以导出和导入的环境,本质上并没有修改代码的执行逻辑,代码执行顺序与模块加载顺序也完全一致。

九、文件监听原理呢?

在发现源码发生变化时,自动重新构建出新的输出文件。

Webpack开启监听模式,有两种方式:

  • 启动 webpack 命令时,带上 --watch 参数
  • 在配置 webpack.config.js 中设置 watch:true

缺点:每次需要手动刷新浏览器

原理:轮询判断文件的最后编辑时间是否变化,如果某个文件发生了变化,并不会立刻告诉监听者,而是先缓存起来,等 aggregateTimeout 后再执行。

module.export = {
    // 默认false,也就是不开启
    watch: true,
    // 只有开启监听模式时,watchOptions才有意义
    watchOptions: {
        // 默认为空,不监听的文件或者文件夹,支持正则匹配
        ignored: /node_modules/,
        // 监听到变化发生后会等300ms再去执行,默认300ms
        aggregateTimeout:300,
        // 判断文件是否发生变化是通过不停询问系统指定文件有没有变化实现的,默认每秒问1000次
        poll:1000
    }
}

十、说一下 Webpack 的热更新原理

Webpack 的热更新又称热替换(Hot Module Replacement),缩写为 HMR。 这个机制可以做到不用刷新浏览器而将新变更的模块替换掉旧的模块。

HMR的核心就是客户端从服务端拉去更新后的文件,准确的说是 chunk diff (chunk 需要更新的部分),实际上 WDS 与浏览器之间维护了一个 Websocket,当本地资源发生变化时,WDS 会向浏览器推送更新,并带上构建时的 hash,让客户端与上一次资源进行对比。客户端对比出差异后会向 WDS 发起 Ajax 请求来获取更改内容(文件列表、hash),这样客户端就可以再借助这些信息继续向 WDS 发起 jsonp 请求获取该chunk的增量更新。

后续的部分(拿到增量更新之后如何处理?哪些状态该保留?哪些又需要更新?)由 HotModulePlugin 来完成,提供了相关 API 以供开发者针对自身场景进行处理,像react-hot-loader 和 vue-loader 都是借助这些 API 实现 HMR。

十一、如何对 bundle 体积进行监控和分析?

VSCode 中有一个插件 Import Cost 可以帮助我们对引入模块的大小进行实时监测,还可以使用 webpack-bundle-analyzer 生成 bundle 的模块组成图,显示所占体积。

bundlesize 工具包可以进行自动化资源体积监控。

十二、在实际工程中,配置文件上百行乃是常事,如何保证各个loader按照预想方式工作?

可以使用 enforce 强制执行 loader 的作用顺序,pre 代表在所有正常 loader 之前执行,post 是所有 loader 之后执行。(inline 官方不推荐使用)

十三、如何优化 Webpack 的构建速度?

说说如何借助webpack来优化前端性能?_小草莓蹦蹦跳的博客-CSDN博客

十四、你刚才也提到了代码分割,那代码分割的本质是什么?有什么意义呢?

代码分割的本质其实就是在源代码直接上线打包成唯一脚本main.bundle.js这两种极端方案之间的一种更适合实际场景的中间状态。

用可接受的服务器性能压力增加来换取更好的用户体验。

源代码直接上线:虽然过程可控,但是http请求多,性能开销大。

打包成唯一脚本:一把梭完自己爽,服务器压力小,但是页面空白期长,用户体验不好。

(Easy peezy right)

十五、webpack解决的问题

模块化的方式开发代码;

使用一些高级的特性来加快我们的开发效率或者安全性;

比如通过ES6+、TypeScript开发脚本逻辑,通过sass、less等方式来编写css样式代码

监听文件的变化来并且反映到浏览器上,提高开发的效率;

模块化JavaScript 、HTML 和 CSS等资源;

将代码进行压缩、合并以及其他相关的优化;

十六、webpack的能力

 ① 编译代码能力,提高效率,解决浏览器兼容问题

 ② 模块整合能力,提高性能,可维护性,解决浏览器频繁请求文件的问题

③ 万物皆可模块能力,项目维护性增强,支持不同种类的前端模块类型,统一的模块化方案,所有资源文件的加载都可以通过代码控制

  • 1
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
webpack的重要知识点包括以下几个方面: 1. 模块化打包:webpack前端的所有资源文件都视为模块,并根据模块的依赖关系进行静态分析,最终打包生成对应的静态资源。 2. 配置文件:webpack使用webpack.config.js文件来配置打包过程。在配置文件中可以设置入口文件、输出路径、加载器、插件等各种参数,以满足项目的需求。 3. 加载器:webpack通过加载器来处理各种类型的文件。常用的加载器有babel-loader用于处理ES6及以上的JavaScript代码,css-loader用于处理CSS文件,file-loader用于处理图片和字体文件等。 4. 插件:webpack的插件用于扩展其功能。常用的插件有HtmlWebpackPlugin用于生成HTML文件,CleanWebpackPlugin用于清理输出目录,MiniCssExtractPlugin用于提取CSS文件等。 5. 开发服务器:webpack-dev-server是一个开发服务器,它可以在内存中编译代码并提供资源,实现快速的开发和调试。 以上是webpack的一些重要知识点,它们可以帮助你更好地理解和使用webpack进行前端资源的构建和打包。<span class="em">1</span><span class="em">2</span><span class="em">3</span> #### 引用[.reference_title] - *1* [webpack打包基础知识点与es6知识点.xmind](https://download.csdn.net/download/qq_43291759/13106867)[target="_blank" data-report-click={"spm":"1018.2226.3001.9630","extra":{"utm_source":"vip_chatgpt_common_search_pc_result","utm_medium":"distribute.pc_search_result.none-task-cask-2~all~insert_cask~default-1-null.142^v93^chatsearchT3_2"}}] [.reference_item style="max-width: 33.333333333333336%"] - *2* [Webpack重要知识点](https://blog.csdn.net/sinat_17775997/article/details/95167425)[target="_blank" data-report-click={"spm":"1018.2226.3001.9630","extra":{"utm_source":"vip_chatgpt_common_search_pc_result","utm_medium":"distribute.pc_search_result.none-task-cask-2~all~insert_cask~default-1-null.142^v93^chatsearchT3_2"}}] [.reference_item style="max-width: 33.333333333333336%"] - *3* [webpack知识总结](https://blog.csdn.net/baidu_39067385/article/details/119428908)[target="_blank" data-report-click={"spm":"1018.2226.3001.9630","extra":{"utm_source":"vip_chatgpt_common_search_pc_result","utm_medium":"distribute.pc_search_result.none-task-cask-2~all~insert_cask~default-1-null.142^v93^chatsearchT3_2"}}] [.reference_item style="max-width: 33.333333333333336%"] [ .reference_list ]

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值