Code Splitting指的是代码分割,那么什么是代码分割,webpack和code splitting又有什么样的联系呢?

使用npm run dev:"webpack-dev-server --config ./build/webpack.dev.js。",会看不到打包生成的dist目录。

所以我们使用一个新的,不要启用dev-server服务。使用npm run dev-build:"webpack --config ./build/webpack.dev.js"。

这个时候我们发现,dist目录生成到了build下面。

我们build下面放到都是webpack配置。这是因为之前webpack移动到了build目录,输出文件到地方没改。直接写dist。指的是dist目录生成在webpack同级的目录下。改成 ../dist。就可以了。

所以webpack的配置项真的是巨多,想完全的能记住是不可能的,所以遇到打包的问题怎么办,首先是打开打包的命令行工具,然后去分析,当你打包的过程开始执行时,他一步一步具体的流程之中哪里出了问题,通过控制台,我们就可以找到这些问题,找到问题后,截取出来,然后到google或者stack overflow上去提问,搜索问题的解决方案,找到后,再去找对应文档上的配置说明,根据文档,再回头去修改我们的配置文件,改的过程中遇到新的问题,再一点一点的去解决。

接着进入正题。Code Splitting到底是什么?代码分割到底是什么?举个例子。

首先我们安装一个包,叫做lodash。

npm install lodash --save

他是一个功能集合,提供了很多工具方法,可以高性能的比如字符串拼装的一些函数。然后继续写代码

index.html
<!DOCTYPE html>
<html lang="en">
  <head>
    <meta charset="UTF-8">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <meta http-equiv="X-UA-Compatible" content="ie=edge">
    <title>html template</title>
  </head>
  <body>
    <div id='root'></div>
  </body>
</html>
index.js
// 一般我们习惯用_去代替lodash。
import _ from "lodash"; console.log(_.join(['a', 'b', 'c'], '*'))

其实他引入了一个库,在这里,使用这个库,做了一个字符串链接这样的操作。最终打印的结果应该是a*b*c这样的字符串。然后我们输入npm run dev-build打包结束后,浏览index.html。发现控制它输出了a*b*c。所以这个函数就是字符串连接的函数。

然后我们看到lodash和我们的业务代码都被打包到一个文件中。我们到main.js有1.38M。非常大。工具库和业务逻辑统一打包到main.js里面。这种方式做打包会带来一个潜在的问题。
第一种方式
假设ladash有1mb,业务逻辑代码1mb。那么main.js 2mb
打包文件会很大,加载时间会很长
当页面业务逻辑发生变化时,又要加载2MB的内容

那么我们需要解决这个问题,在src目录下,我再创建一个文件,叫做lodash.js。然后将lodash的引入放放到lodash.js文件里面

lodash.js

// 一般我们习惯用_去代替lodash。
import _ from "lodash";
window._ = _;
index.js
console.log(_.join(['a', 'b', 'c'], '*'))

webpack.common.js

module.exports = {
  entry: {
    lodash: './src/lodash.js',
    main: './src/index.js'
  }
}
再运行npm run dev-build。发现打包出来两个文件。这个时候lodash就跟index.js分开加载了。之前用户需要加载完2MB的页面才能加载页面。现在我们把main.js分成了两个文件,分别是lodash.js和index.js。这是时候我们去想,
第二种方式
main.js被拆成lodash.js,index.js,分别是1mb。
当页面业务逻辑发生变化时,只要加载main.js即可。

这种代码的拆分,就是我们代码的核心概念.CodeSplitting。没有代码拆分完全可以,但是有代码拆分会提升性能。第二种方式是我们自己做的代码分割。不够智能。在webpack里面使用一些插件,可以智能的帮我们做code split。那么我们接下来看webpack这么自动帮我们做

index.html

<!DOCTYPE html>
<html lang="en">
  <head>
    <meta charset="UTF-8">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <meta http-equiv="X-UA-Compatible" content="ie=edge">
    <title>html template</title>
  </head>
  <body>
    <div id='root'></div>
  </body>
</html>

index.js

import _ from "lodash";
console.log(_.join(['a', 'b', 'c'], '*'))

webpack.common.js

module.exports = {
  // 优化
  optimization: {
    // 帮我们做代码分割
    splitChunks: {
      chunks: 'all'
    }
  }
}

然后运行npm run dev-build。看运行结果,webpack是怎么帮我们做代码分割的。

打包生成的文件除了main.js。还多出了一个文件,叫做vendors~main.js。我们打开main.js,发现里面有index的业务逻辑,但是并没有lodash。再打开vendors~main.js。发现他自己把lodash提取出来。我们只做了一个非常简单的配置,webpack自己就知道了当遇到这种公用的类库的时候,自动就打包生成文件。这就是我们webpack的code splitting。所以说代码分割是webpack非常有竞争力的功能

当然,webpack里面的代码分割不仅仅可以通过这种配置完成。我们还可以通过另外一种方式进行webpack中的代码分割。之前的那种方式是,index.js的lodash和业务逻辑是同步的。webpack通过分析去做分割。那实际上。我们除了同步的去做代码分割之外,我们还可以异步的去进行加载第三方类库。

index.html

<!DOCTYPE html>
<html lang="en">
  <head>
    <meta charset="UTF-8">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <meta http-equiv="X-UA-Compatible" content="ie=edge">
      <title>html template</title>
  </head>
  <body>
    <div id='root'></div>
  </body>
</html>

index.js

function getComponent() {
  // 异步调用的lodash返回回来后,会放到_这个变量里
  return import('lodash').then(( {default: _} )=>{
    var element = document.createElement('div');
    element.innerHTML = _.join(['1', ' ', '2'], '-');
    return element;
  })
} getComponent().then(element => {
  document.body.appendChild(element);
})

然后npm run dev-build。发现会报错

说不支持这种动态import的方式。这个时候我们需要一个webpack的第三方库。帮助我们去支持这种引入方式。

npm install babel-plugin-dynamic-import-webpack --save-dev
.babelrc
{
  "presets": [
    ["@babel/preset-env",{
      "targets": {
        "chrome": "67",
      },
      "useBuiltIns": "usage",
      "corejs": 3
    }],
    "@babel/preset-react"
  ],
  "plugins": ["babel-plugin-dynamic-import-webpack"]
}

然后重新的去打包,已经没有问题了。这个时候,我们再打开dist目录。除了main.js,还有一个0.js。main.js只有业务代码。0.js里面打包了lodash。也就是说,webpack在做同步性质的打包的时候,直接上面 import _ from 'lodash'。然后他会分析代码,自动的分割出lodash。现在代码是异步加载的时候。webpack也会去做代码的分割。

总结:

1、代码分割跟webpack无关

2、所以webpack分割代码有两种方式,一种是同步的方式,靠
optimization: {
  // 帮我们做代码分割
  splitChunks: {
    chunks: 'all'
  }
},
这个配置。

一种是异步的方式,无需做任何配置,会自动进行代码分割。需要额外的安装 babel-plugin-dynamic-import-webpack 支持。

webpack 和 code splitting的更多相关文章

  1. webpack 利用Code Splitting 分批打包、按需下载

    webpack中的解决方案——Code Splitting,简单来说就是按需加载(下载),如果是requireJS对应的AMD的方案中这本是在正常不过了.但是在webpack中All in one的思 ...

  2. Webpack之Code Splitting 代码分块

    如何实现代码分块 默认情况webpack会将资源文件打包成一个js文件,比如app.bundle.js 实际情况我们需要按需加载 方法如下: require.ensure(dependencies, ...

  3. webpack Code Splitting浅析

    Code Splitting是webpack的一个重要特性,他允许你将代码打包生成多个bundle.对多页应用来说,它是必须的,因为必须要配置多个入口生成多个bundle:对于单页应用来说,如果只打包 ...

  4. [Webpack 2] Maintain sane file sizes with webpack code splitting

    As a Single Page Application grows in size, the size of the payload can become a real problem for pe ...

  5. webpack优化之code splitting

    作为当前风头正盛的打包工具,webpack风靡前端界.确实作为引领了一个时代的打包工具,很多方面都带来了颠覆性的改进,让我们更加的感受到自动化的快感.不过最为大家诟病的一点就是用起来太难了. 要想愉快 ...

  6. [转] react-router4 + webpack Code Splitting

    项目升级为react-router4后,就尝试着根据官方文档进行代码分割.https://reacttraining.com/react-router/web/guides/code-splittin ...

  7. react-router4 + webpack Code Splitting

    项目升级为react-router4后,就尝试着根据官方文档进行代码分割.https://reacttraining.com/react-router/web/guides/code-splittin ...

  8. webpack async load modules & dynamic code splitting

    webpack async load modules & dynamic code splitting webpack 按需/异步加载/Code Splitting webpack loade ...

  9. 借助Code Splitting 提升单页面应用性能

    近日的工作集中于一个单页面应用(Single-page application),在项目中尝试了闻名已久的Code splitting,收获极大,特此分享. Why we need code spli ...

随机推荐

  1. Mybatis使用Spring data Pageable的方法

    引言 可能这个用法是个邪教了...但是简单说这都是历史缘故,貌似是项目最初用JPA后面还是换Mybatis了,我接手时候看着那个写好的Controller层觉得换了怪可惜的,就沿用了.网上找找,提供的 ...

  2. 【miscellaneous】关于gst ffmpeg插件的安装心得

    1 一直通过软件源不能将ffmpeg插件进行安装 2 下载源码编译一直失败 说是需要依赖bad插件 3 bad插件安装不上在ubuntu下 解决办法: 应该直接查找ffmpeg插件的安装办法,不是只有 ...

  3. Opencv官方例程简介

    opencv sample文件夹例程 No1. adaptiveskindetector.cpp 利用HSV空间的色调信息的皮肤检测,背景不能有太多与肤色相似的颜色.效果不是特别好. No2. bag ...

  4. [CF293B]Distinct Paths_搜索_剪枝

    Distinct Paths 题目链接:http://codeforces.com/problemset/problem/293/B 数据范围:略. 题解: 带搜索的剪枝.... 想不到吧..... ...

  5. Greenplum 5.21.1 集群安装部署

    简单来说GPDB是一个分布式数据库软件,其可以管理和处理分布在多个不同主机上的海量数据.对于GPDB来说,一个DB实例实际上是由多个独立的PostgreSQL实例组成的,它们分布在不同的物理主机上,协 ...

  6. ubuntu 快捷方式添加 applications添加

    首先我们要了解,Ubuntu 的 Dash 里所有程序都是在 /usr/share/applications 中的,所以我们的思路很简单——建一个类似于“快捷方式”一样的东西扔进去就好了.所以第一步自 ...

  7. java之理解面向对象

    1.程序设计的三种基本结构 顺序结构 顺序结构表示程序中的各操作是按照它们在源代码中的排列顺序依次执行的 选择结构 选择结构表示程序的处理需要根据某个特定的条件选择其中的一个分支执行.选择结构有单选择 ...

  8. 设计Qt风格的C++API

    在奇趣(Trolltech),为了改进Qt的开发体验,我们做了大量的研究.这篇文章里,我打算分享一些我们的发现,以及一些我们在设计Qt4时用到的原则,并且展示如何把这些原则应用到你的代码里. 优秀AP ...

  9. 普通表分区改造_rename方式

    一.需求 配合开发人员,对业务临时表进行分区改造(业务认为的临时表,只需要保留近一月数据,并非oracle临时表类型) 二.如下记录完整过程 开发需求 TS_PM 以time_key分区 .沟通明确方 ...

  10. MD5加密处理

    无论传送过程和存储方式,都是以明文的方式,很不安全!一旦泄漏,将会造成很大的损失! 插件名称jQuery.MD5.js: /** * jQuery MD5 hash algorithm functio ...