美文网首页帖子收藏
webpack打包之Library打包

webpack打包之Library打包

作者: 喜剧之王爱创作 | 来源:发表于2020-09-01 19:14 被阅读0次
    panyan.jpg

    写在前面

    之前写下了《webpack4入门讲解》文集,里面从webapck最基础概念,到一些高级的配置,处理分包等问题,读完后你会对webpack有一个比较清晰的认识,从这一节开始,我们要去学习一些webpack的高级使用实际,在实际开发中,你可能会遇到一些比如打包优化等等方面的内容,这个文集中将详细介绍,同时,为了保证知识涵盖面的广泛,还会将到一些你开发中可能用不到的内容,大家各取所需即可。当然,基础还不扎实的同学,要去学习前面的文集哦,前面的文集可不是各取所需,如果可以,我希望你将它彻底搞懂。
    下面进入本文集的第一篇文章

    Library打包

    什么是“Library”?

    所谓Library即“库”,比如我们使用的lodash就是一个“函数库”,比如我们的常用的'antd'、'elementUI'这些就属于“组件库”,在实际的工作中,我们很有可能去封装自己的函数库或者是UI组件库或者是基于某个开源库做二次封装的业务组件库,那么我们是入库针对“库”进行打包的呢?

    环境准备
    • 创建一个名为'library'的文件夹,执行npm init -y,初始化一个npm环境。
      生成的package.json如下
    {
      "name": "library", // 库的名字
      "version": "1.0.0", // 库的版本
      "description": "", // 库的描述
      "main": "index.js", // 入口
      "scripts": { // npm指令
        "test": "echo \"Error: no test specified\" && exit 1" // 可以删掉,创建我们自己的指令
      },
      "keywords": [],
      "author": "yourname", // 库的作者
      "license": "ISC" // 协议,可以改成‘MIT’开源协议
    }
    
    • 写一个自己的库

    在根目录下创建如下文件目录

    |--src
      |--math.js
      |--string.js
      |--index.js 
    

    其中内容如下

    // math.js
    export function add (a, b) {
        return a+b
    }
    export function minus (a, b) {
        return a-b
    }
    export function multiply (a, b) {
        return a*b
    }
    export function division (a, b) {
        return a/b
    }
    
    // string.js
    export function join(a, b) {
        return a + ' ' + b
    }
    
    // index.js
    import * as math from './math'
    import * as string from './string'
    export default { math, string }
    

    上面的代码中,我们就简单的实现了一个自己的库,其中包括加减乘除的数字运算和字符串的拼接,实际上,一个库的开发,就类似于一个业务系统,他也是需要被打包才能被使用,所以我们还需要webpack对其进行打包

    • 安装webpack并创建webpack.config.js配置文件
    yarn add webpack webpack-cli -S
    

    webpack.config.js

    const path = require('path')
    
    module.exports = {
        mode: 'production',
        entry: './src/index.js',
        output: {
            path: path.resolve(__dirname, 'dist'),
            filename: 'library.js'
        }
    }
    

    package.json中增加打包指令

      "scripts": {
        "build": "webpack"
      }
    
    • 执行打包

    我们看到在根目录'dist'文件夹下生成了一个'library.js'的文件,如果是对于我们平常的业务代码,到这一步,我们已经完成了,但是我们是开发一个库的代码,是要给别人用的,别人用的形式可能是下面这样的

    import library from 'library' // ESM
    
    const library = require('library') // commonJs
    

    于是我们在配置文件中加入一个配置项如下

    module.exports = {
      output: {
        libraryTarget: 'umd'
      }
    }
    

    意思是,无论你使用什么样的引入方式,我们打包出来的库都支持。有时候我们还有可能是通过script标签进行引入的

    <script src='library.js'></script>
    // 在使用的时候,通过library这样的全局变量来使用,就像jquery那样
    

    那么我们还需要在配置项中加入下面的配置

    module.exports = {
      output: {
        library: 'library' // 名字随便取,代表我们全局暴露的变量
      }
    }
    
    • 执行打包,打包依然是生成了一个'library.js'的文件,下面我们通过一个简单的html文件来验证一下我们的打包结果,这里就是个html通过script标签引入,然后测试全局变量,自行测试。
    关于libraryTarget和library的配置关系

    实际上,在做library打包的时候是,libraryTargetlibrary是有一定的关系的,需要配合使用

    • library作为核心,代表要生成一个全局变量
    • libraryTarget意思是这个全局变量挂在哪里,如果是umd,那么二者是没有关系的,如果是this,就代表我们的库不再支持AMD,commonJS,esm等模块形式,而是将全局变量注入到全局的this上面。其中libraryTarget可以取值umdthiswindowglobal(nodeJs下)等值,一般我们在封装一个库的时候,会选择umd

    关于libraryTargetlibrary,其实其内容也是比较多的,这里我们只做简单的介绍,如果你的真的需要去打包这样的库的话,再去翻阅相关资料

    在Library中使用第三方库

    有时候,我们在封装自己的库的时候,不是所有的方法都自己写的,我们也会去引用一些第三方的组件库或者函数库,比如在上面的例子中,我们做下面的代码变更

    // string.js
    import _ from 'lodash'
    export function join(a, b) {
        return _.join([a,b], ' ')
    }
    

    这时候打包,也是能正常打包的,但是,library文件却比之前大了很多,这是因为我们打包进了lodash这个库,但是用户在使用我们的库的时候,可能在业务代码中也会引入lodash这个库,这个时候,打包的代码,很可能就会打包出两份lodash,从而中造成一些问题,为了解决这个问题,我们需要这样去配置

    externals
    module.exports = {
      externals: ['lodash']
    }
    

    做了上面配置后,我们发现,我的库打包后又变小了,那么externals的意思是啥呢?就是我们在打包的时候,遇到这个库就忽略他,不要把他打包到代码中,具体的配置,大家可以看一下官网的API,其中,externals可以配置为对象,并且有几个参数,这里我们只讲解commonjsroot,大家就知道怎么回事了

    commonjs

    我们将配置改成这样

    module.exports = {
        externals: {
            lodash: {
                commonjs: 'lodash'
            }
        }
    }
    

    上面配置的意思是,当我使用commonjs规范做打包的时候,遇到lodash这个库,我们必须使用'lodash'这个名字,就像这样

    const lodash = require('lodash')
    const _ = require('lodash') // 这是错误的!!
    
    root
    module.exports = {
        externals: {
            lodash: {
                root: '_',
                commonjs: 'lodash'
            }
        }
    }
    

    这代表,我们不使用模块化,而是用script标签做引入的话,这时候,我们必须全局注入一个'_'的变量

    当然了一般情况下,我们都是直接

    module.exports = {
        externals: {
            lodash: 'lodash'
        }
    }
    

    意思是,不管是怎么引入,我们都使用'lodash'这个名字。
    这里我们只是对library的打包,做了一个相对简单的介绍,实际上,当你要去真正开发一个组件库的时候,其打包文件也是比较复杂的,到时候大家再去学习,这里通过library的打包,让大家知道几个概念和配置项

    将包发布到npm

    我们将库封装好了以后,一般会将库发布到npm上去,这里就再代价感受一下,将自定义的库发布到npm上

    1. 修改配置文件中的main
    "main": "./dist/library.js"
    

    将main改成我们将来要给用户去用的文件

    1. 到npm官网去注册一个npm账号
    2. 根目录下执行npm adduers,添加用户名密码
    3. 运行npm publish,将包发布到npm仓库中,但是,我们的仓库名很容易和线上已有包重名,造成发布失败,这就需要我们把名字起的独特一点,如果你的在cnpm私库下面,还需要有作用域来解决这一问题。
    4. npm install 试试使用的库吧!

    写在后面

    本文介绍了关于库即Library的打包方式,和一些webpack中比较高级的概念,大家可以试着去写一个自己的库试试哦!

    相关文章

      网友评论

        本文标题:webpack打包之Library打包

        本文链接:https://www.haomeiwen.com/subject/ueuvsktx.html