构建webpack知识体系 | 青训营笔记

这是我参与「第四届青训营 」笔记创作活动的的第4天。

进阶中高级前端工程师,对webpack打包构建工具的掌握是必不可少的。我也曾经看过许多webpack教程,但无非是记记某些模式怎么配置,根本就没有认识到webpack的魅力,借此次青训营的机会,希望范文杰老师能给我带来不一样的收获。如果你也想了解的话,不妨接着看下去。

我们总是听说前端要具备工程化思维,那到底什么是工程化思维呢?这里我给出一段从知乎上摘抄的定义,

狭义上的理解:将开发阶段的代码发布到生产环境,包含:构建,分支管理,自动化测试,部署

广义上理解:前端工程化应该包含从编码开始到发布,运行和维护阶段


一、什么是webpack?

前端项目是由很多资源文件组合而成,为了保证代码的正确运行,要考虑文件之间的引用关系,必须严格按照依赖顺序书写代码,除此之外,还有很多其他问题,大大影响开发效率。

为了解决这些问题,市面上出现了很多工具,如gulp、rollup、vite等,其中目前最具影响力、应用最为广泛的当属webpack。

webpack本质上是一种前端资源编译、打包工具。


二、使用webpack

示例

1、安装

npm i -D webpack webpack-cli

2、编辑配置文件——webpack.config.js

const path = require('path')

module.exports = {
    entry: './src/index',
    mode: 'development',
    devtool: false,
    output: {
        filename: `[name].js`,
        path: path.join(__dirname, './dist')
    }
}

我来解释一下上面导出内容是什么意思:entry是打包的入口文件,mode则是打包模式,一般会有开发环境和生产环境的区别,

output则是出口文件,用于指定文件打包后的位置

3、执行编译命令

npx webpack

三、webpack打包的核心流程——极度简化版

  1. 入口处理——从’entry’文件开始,启动编译流程
  2. 依赖解析——从’entry’文件开始,根据’require’ or 'import’等语句找到依赖资源
  3. 资源解析——根据’module’配置,调用资源转移器,将png、css等非标准js资源转译成js内容
  4. 资源合并打包——将转译后的资源内容合并打包为可直接在浏览器运行的js文件

四、使用webpack

关于webpack的使用方法,基本都围绕“配置”展开,而这些配置大致可划分为两类:

——流程类:作用于流程中某个或若干个环节,直接影响打包效果的配置项

——工具类:主流程之外,提供更多工程化能力的配置项

1、处理js文件

其实处理使用es6之前的语法编写的js文件是不需要额外安装插件的,其配置文件和上面代码并无二致。

2、处理css文件

首先在入口文件引入对css依赖,

import './index.css'

console.log("hello world")

然后再通过npm安装对应的loader

npm i style-loader css-loader

配置webpack文件

const path = require('path')

module.exports = {
    entry: './src/index',
    mode: 'development',
    devtool: false,
    output: {
        filename: `[name].js`,
        path: path.join(__dirname, './dist')
    },
    module: {
        rules: [{
            test: /\.css$/,
            use: ['style-loader', 'css-loader']
        }]
    }
}

第一次看到这段代码你可能会有点懵,我来帮你解释一下。

rules中的test后面跟的是一个正则表达式,上述正则表达式含义是匹配以.css结尾的文件,

use后面跟着的则是对应使用的loader去处理文件

3、处理es6+代码

如上面所说,处理es6之前的代码是无需下载其它loader的,基本所有的浏览器都提供对es5的支持,为了让开发者能享受到新语法的简便同时兼顾对其它浏览器的兼容,babel这个插件就大放异彩。

再入口文件书写es6代码

class Person {
    constructor() {
        this.name = 'ExMaterial'
    }
}

console.log((new Person()).name)
const say = () => {}

然后再通过npm安装对应的loader

npm i -D @babel/core @babel/preset-env babel-loader

配置文件

const path = require('path')

module.exports = {
    entry: './src/index',
    mode: 'development',
    devtool: false,
    output: {
        filename: `[name].js`,
        path: path.join(__dirname, './dist')
    },
    module: {
        rules: [{
            test: /\.js$/,
            use: [{
                loader: 'babel-loader',
                options: {
                    presets: [
                        ['@babel/preset-env']
                    ]
                }
            }]
        }]
    }
}

4、处理html

处理html就不像上述代码是再module中继续使用loader,而是要用到一个新的配置项——plugins。

webpack官网对plugins的解释是——While loaders are used to transform certain types of modules, plugins can be leveraged to perform a wider range of tasks like bundle optimization, asset management and injection of environment variables.(虽然loaders用于转换某些类型的模块,但是插件可以用来执行更广泛的任务,如捆绑包优化、资源管理和环境变量注入。)

这里给出官网的一段配置代码:

const HtmlWebpackPlugin = require('html-webpack-plugin');
const webpack = require('webpack'); //to access built-in plugins

module.exports = {
  module: {
    rules: [{ test: /\.txt$/, use: 'raw-loader' }],
  },
  plugins: [new HtmlWebpackPlugin({ template: './src/index.html' })],
};

————————————————————分割线————————————————————

聊了上面那些东西后,再来说一点其它类似“黑科技”的配置

1、HMR-Hot Module Replacement-模块热替换

何为热替换,即你修改代码后,页面会自动刷新,而无需开发者手动刷新,现在前端各种框架的脚手架同理。

其实webpack已经内置这个功能了,要开启只需要自己在webpack.config.js中配置一下就好了

module.exports = {
  // ...
  devServer: {
    hot: true
  }
};

2、Tree-Shaking-树摇

用于删除没有用到的代码,减小打包后的体积

module.exports = {
  // ...
  mode: "production",
  optimization.usedExports: true
};

此外,还有很多其它工具:

  • 缓存
  • Sourcemap
  • 性能监控
  • 日志
  • 代码压缩
  • 分包

进阶篇plugins的内容就不写了,那么今天的分享就到此结束了。

你可能感兴趣的:(学习笔记,webpack,前端,javascript)