webpack5 基础配置 11 性能优化 预加载预请求,cdn shimming

动态导入的懒加载

像很多vue,react路由懒加载就是这样的,通过()=>import(’./xxx’)实现路由一个懒加载
实现一个组件懒加载
webpack5 基础配置 11 性能优化 预加载预请求,cdn shimming_第1张图片
webpack5 基础配置 11 性能优化 预加载预请求,cdn shimming_第2张图片
打包后的文件在这
webpack5 基础配置 11 性能优化 预加载预请求,cdn shimming_第3张图片
webpack5 基础配置 11 性能优化 预加载预请求,cdn shimming_第4张图片
可以看到一开始是没有加载我们的element.js文件的,当我们点击后
webpack5 基础配置 11 性能优化 预加载预请求,cdn shimming_第5张图片
可以看到已经生成了一个文件。webpack5 基础配置 11 性能优化 预加载预请求,cdn shimming_第6张图片
打印出来是一个对象,导出的元素就在这个default里面。
这就是懒加载的应用。

懒加载优化

上面那个例子点击按钮后大概是发生了两个步骤。第一个是下载element.js这个文件,第二个是浏览器解析运行js代码。
我们现在希望,当首页加载完,就是浏览器空闲下来的时候,我们就去请求这个文件,而不是等我们点击后再去请求。
webpack已经帮助我们实现了这个功能,只需要我们配置下,
webpack5 基础配置 11 性能优化 预加载预请求,cdn shimming_第7张图片
魔法注射,跟命名一样,webpackPrefetch,pre提前的,fetch请求,提前请求。webpack5 基础配置 11 性能优化 预加载预请求,cdn shimming_第8张图片
在我们刷新完之后。他就会去请求,总是在最后面才请求。在这里插入图片描述
当我们点击按钮后,他是从缓存中去拿这个文件并加载。

除了prefetch,还有preload,

preload的作用是也是提前下载,但他是在父文件,也就是代码所在的文件被加载的时候,以并行方式开始下载,而prefetch是会在父文件加载完后加载。preload具有中等优先级,是会立即下载,用于当下时刻。而prefetch是在浏览器闲暇时下载,用于未来的某些时刻。
一般路由是设置preloade,而组件一般通过prefetch,一些用户可能不会点击到的就不做预加载处理。

补充 optimization.runtimeChunk配置.

optimization这个属性主要是用来性能优化的,比如chunkIds,splitChunks,还有runtimeChunk。
webpack5 基础配置 11 性能优化 预加载预请求,cdn shimming_第9张图片
runtime相关的代码就是对模块引入的时候,比如import啊,require这些啊,就是通过runtime代码完成的。默认是放到main.bundle.js主模块中。或者是index.bundle.js。也就是runtime的代码是没有抽离出来的。webpack5 基础配置 11 性能优化 预加载预请求,cdn shimming_第10张图片
当我们设为true时,默认会打包出两个文件。为什么有两个呢,因为index与main都有runtime的代码。设为multiple与true效果一样
还有值为single,简单的意思。 只会打包一个包webpack5 基础配置 11 性能优化 预加载预请求,cdn shimming_第11张图片
还可以设置一个对象,
webpack5 基础配置 11 性能优化 预加载预请求,cdn shimming_第12张图片
name属性设置名字。name值还可以写上函数 webpack5 基础配置 11 性能优化 预加载预请求,cdn shimming_第13张图片
传一个入口对象进来。webpack5 基础配置 11 性能优化 预加载预请求,cdn shimming_第14张图片
根据name值不同也生成了两个文件。

认识CDN shimming DLL

认识CDN
webpack5 基础配置 11 性能优化 预加载预请求,cdn shimming_第15张图片
CDN内容分发网络,简单地说就是通过相互连接的网络系统,通过利用靠近客户的服务器来给客户提供更好的体验,提高性能,降低成本。
假如A要请求一张图片a,但是a的服务器离他很远,而A的旁边有很多CDN,所以最靠近A的节点被我们称作边缘节点,他有一个父节点,父节点连接着源节点/原站。服务器会把数据a放在源站,然后第一次请求a时,A通过边缘节点向父节点发送请求,父节点向原站发送请求,拿到数据然后自己备份一份,在传给边缘节点,边缘节点备份后返回给A,下次假设有B也是同一个边缘节点也想访问a,因为有缓存了,所以会直接返回。假设有C,不同同一个边缘节点,但他们的边缘节点的父节点都是同一个,那么C会通过边缘节点向父节点发送请求,父节点因为缓存过了,所以直接返回。大大提高了性能。

在webpack中怎么使用cdn呢

webpack5 基础配置 11 性能优化 预加载预请求,cdn shimming_第16张图片
第二种方式是自己的代码放到自己的服务器,第三方的代码放到cdn去。
第一种方式需要购买cdn服务器。
配置的话就是直接修改output.PublicPath,在打包时添加上自己的CDN地址。这个属性我们之前讲过,我们的index.html文件的script的src路劲就是域名+publicPath(默认是’’)+文件名
webpack5 基础配置 11 性能优化 预加载预请求,cdn shimming_第17张图片
webpack5 基础配置 11 性能优化 预加载预请求,cdn shimming_第18张图片
然后配置路劲
webpack5 基础配置 11 性能优化 预加载预请求,cdn shimming_第19张图片
webpack5 基础配置 11 性能优化 预加载预请求,cdn shimming_第20张图片
可以看到已经配置成功了。这样去加载时,就会去cdn上面加载。(公司用得不多)

更常见的做法 利用第三方库的cdn服务器。

找到第三方库,配置webpack.config.js的externals属性(与output同级),因为我们的第三方库一般是打包到vendors.js文件(通过optimization.splitChunks.cacheGroup)配置。所以要通过externals告诉webpack,哪些第三方库不要打包进去。然后在打包的index.html配置cdn地址,如Lodash与dayjs这两个模块。
webpack5 基础配置 11 性能优化 预加载预请求,cdn shimming_第21张图片
第三方库一些是免费的。怎么配置呢
webpack5 基础配置 11 性能优化 预加载预请求,cdn shimming_第22张图片
打包完发现,vendor.js的包已经不见了,证明第三方库不被打包进去。
webpack5 基础配置 11 性能优化 预加载预请求,cdn shimming_第23张图片
当时代码跑起来时会报错的,因为没有第三方库的代码,也没有配置cdn。
接着我们要在Index.html模板上手动加上cdnwebpack5 基础配置 11 性能优化 预加载预请求,cdn shimming_第24张图片
里面的cdn需要我们去官网找。(这种方法较为推荐)
但是这样配置不太好,因为开发生产模式都会用这种方式。比如我们开发的时候本地服务就很快,还要跑cdn的话是比较多余的。webpack5 基础配置 11 性能优化 预加载预请求,cdn shimming_第25张图片
可以看下打包后的index.html文件,cdn是没有加defer的,就是说下载完就会立即执行。
在开发环境中,没有必要使用cdn。
webpack5 基础配置 11 性能优化 预加载预请求,cdn shimming_第26张图片
放到prod(图放错了)里面去,然后在Index.html模板上使用模板引擎在这里插入图片描述
因为我们这个模板是ejs模板,可以使用外部传入变量。又因为我们一开始设置了一个值,porcess.env.NODE_ENV,所以就可以在ejs模板里面拿到这个值。
npm run serve 打开开发模式
webpack5 基础配置 11 性能优化 预加载预请求,cdn shimming_第27张图片
没有刚才拿东西了,build一下webpack5 基础配置 11 性能优化 预加载预请求,cdn shimming_第28张图片
可以看到生产模式下是cdn,开发模式下是本地服务器。

认识shimming(webpack不推荐使用)

webpack5 基础配置 11 性能优化 预加载预请求,cdn shimming_第29张图片
比如我们现在引入了一个abc的库,这个库依赖于lodash,但是他没对他做引用,就是在abc的库的源码没有import lodash这个库,abc认为你的源代码引入了lodash库,所以当我们运行的时候就会报错。
webpack5 基础配置 11 性能优化 预加载预请求,cdn shimming_第30张图片

所以shimming的作用就出来了,只要有某个东西引入了某个库,那么就自动导入这个库。
webpack内置一个插件叫ProvidePluginwebpack5 基础配置 11 性能优化 预加载预请求,cdn shimming_第31张图片
只要这样配置,就可以了。这个插件的作用是,当我们遇到的某个变量找不到时,会自动导入对应的库。webpack5 基础配置 11 性能优化 预加载预请求,cdn shimming_第32张图片
但是webpack不推荐这么用。因为webpack是提倡模块化,一旦我们用了这方式,webpack会不知道哪个模块对应哪个模块,我们需要编写封闭性的,不存在隐含依赖的彼此隔离的代码。
这是shimming的一个功能。还有另外的功能

shiming的MiniCssExtractPlugin

我们现在的代码都是通过js分离的,css没有,我们想分离css代码,就可以通过这个插件了。将css文件抽到单独的文件。
webpack5 基础配置 11 性能优化 预加载预请求,cdn shimming_第33张图片
我们这样打包后是不会生成一个单独的文件的。
webpack5 基础配置 11 性能优化 预加载预请求,cdn shimming_第34张图片

安装 cnpm install mini-css-extract-plugin -D
生产环境才需要分离
webpack5 基础配置 11 性能优化 预加载预请求,cdn shimming_第35张图片
所以在prod文件配置,filename是文件名和路劲,单单这样还不够,这个插件也内置了自己的Loader,我们之前使用style-loader来解析css,但是生产环境下不需要style-loader
webpack5 基础配置 11 性能优化 预加载预请求,cdn shimming_第36张图片
webpack5 基础配置 11 性能优化 预加载预请求,cdn shimming_第37张图片

如果是开发模式,会返回undefined,如果是生产模式,会返回true
在这里插入图片描述

webpack5 基础配置 11 性能优化 预加载预请求,cdn shimming_第38张图片
改装成一个函数返回一个对象
所以引入这个插件后把style-loader换掉打包
webpack5 基础配置 11 性能优化 预加载预请求,cdn shimming_第39张图片
这样就生成css文件了。

hash contenthash chunkhash

hash的区别
webpack5 基础配置 11 性能优化 预加载预请求,cdn shimming_第40张图片
为什么有runitme的文件,因为只要是模块化,webpack通过runtimeChunk就会帮我们打包。
哈希值一摸一样,这个hash是怎么来的呢,是通过整个项目来的,也就是说,只要项目有一处地方改变,hash值就会改变。那么其他文件名也会改变,也会重新编译。
所以我们改成ChunkHashwebpack5 基础配置 11 性能优化 预加载预请求,cdn shimming_第41张图片
可以看到chunkhash的hash值也不是一样的,也就是说改变一个文件的内容,只会修改那个文件的内容和名字,其他文件不会重新编译一下。但是这种情况也有缺点,比如我们打包css文件的时候,filename也是用chunkhash,那么这个css文件的chunkhash值跟引入他的文件的chunkhash值是一样的,比如main.js。那么main.js文件只要改变一点内容,除了main.js的打包文件的chunkhash会改变,css文件的名字也会改变,因为他们是同个chunkhash,所以这样也不行。

我们使用contenthash,

顾名思义,以内容来计算hash值,设置这个之后,一个文件的内容就智能影响自己的文件。webpack5 基础配置 11 性能优化 预加载预请求,cdn shimming_第42张图片
所以推荐,每个独立的包使用contenthash,包括chunkFilename,而我们打包的Bunle.js就使用chunkhash。

小结 主要的内容还是性能优化,首先是懒加载时候的优化,魔法注射的webpackPrefetch预请求,webpackload预加载。这个是对懒加载加载的组件代码,路由代码等进行优化。还补充了一点optimization的runtimeChunks的配置,这个配置主要是对模块化的代码是否要进行一个抽离,主要是引用了一个插件,并且可以设置filename。只要配置了这个属性,只要是模块化就会打包成另外的文件,就算没有import等等,因为webpack默认就是模块化。

接着就是CDN的认识,CDN说白了就是服务器把资源放到原站,用户通过边缘节点-父节点-原站等进行请求返回,并且做缓存设置,方便下一个用户拿到。CDN在webpack的配置有两种,一种是直接全部打包到cdn去,另一种是自己的代码放到服务器,第三方库使用cdn。第一种主要是在entry里面的punlicPath去配置CDN域名。第二种是通过extenals属性(在Prod生产文件配置),去配置不打包的第三方库,然后通过修改ejs模板的index.html,在里面通过我们设置的process.env.NODE_ENV去获取当前是什么环境,开发的话什么都不做,因为全部资源放在本地服务器最方便。生产的话,就引入我们要用的第三方库的cdn。

接着就是shimming的认识,其中一个功能就是自动补齐缺少的第三方库,使用weboak内置的ProvidePlugin来配置哪些第三方库需要自动补齐

webpack5 基础配置 11 性能优化 预加载预请求,cdn shimming_第43张图片

还有一个功能就是分离css,通过一个插件mini-css-extract-plugin在生产模式下配置,所以就需要判断当前是什么模式,而且这个插件也内置了一个Loader,来代替style-loader,因为生产模式时不需要style-loader的,所以要用这个插件的内置loader来处理,最后就能正常打包成单独的css文件了。

最后就是hash值的不同的,首先第一个hash,最普通,也不推荐用,因为这个hash值是通过整个项目来进行推算的,也就是说,当有一个文件改变内容,这个hash值就会改变,导致所有文件的文件名都改变,都需要重新编译,浪费性能。第二种就是chunkhash,顾名思义就是通过chunk的内容,当我们设置这个值后,普通Js文件之间不会相互影响,但是其他的资源比如css,main.js里面引入了css,只要main.js的文件以改变。css的文件的chunkhash值也会改变,导致重新编译。所以就有第三种,contenthash,顾名思义,通过内容计算hash值,用这个hash值后,每个文件都只会影响自己。所以一般推荐,单独的包或者chunkFilenames都是用contenthash,而打包的bundle.js使用chunkhash.

部分图片来自codeywhy老师

你可能感兴趣的:(webpack5 基础配置 11 性能优化 预加载预请求,cdn shimming)