Webpack5快速入门(一)手把手带你打开前端工程化的大门

目录

一、Webpack简介

webpack是什么🐟

学习Webpack的目的🐟

Webpack功能🐟

二、Webpack上手

一个例子告诉你为什么需要webpack 🐬

webpack登场🐬

三、Webpack配置文件

webpack局部打包 🐋

自定义入口文件名🐋

自定义输出目录 🐋

通过package.json自定义配置🐋

npm与npx的区别🐋

通过webpack.config.js配置🐋

总结 🐋

四、Webpack依赖图


大家好,这里是小杰😁😁😁,从今天开始我们就进入了前端工程化的学习,这是第一期,webpack会作为一个专栏持续更新,如果你刚刚学完前端三剑客,不知道下一步该学什么,或者你是一个webpack的初学者那么就让我们一起由浅入深探索一下webpack的世界吧!✌️

一、Webpack简介💨

webpack是什么💦

 Webpack是一种前端资源构建工具,一个静态模块打包器 

 在 Webpack看来,前端的所有资源文件(js/json/css/img/less/...)都会作为模块处理 

 它将根据模块的依赖关系进行静态分析,打包生成对应的静态资源(bundle) 

学习Webpack的目的💦

很简单,就是为了 通过Webpack实现项目工程化 

Webpack功能💦

打包:将不同类型资源按模块处理进行打包

静态:打包后最终产出静态资源

模块:webpack支持不同规范的模块化开发,例如commonjs ,ES module等等

二、Webpack上手💨

首先我们在命令行里查看一下自己webpack的版本号:

如果没有安装的同学,可以去看官方文档安装。

然后我们再构建一下项目的目录:

在webpack初体验文件夹下新建src文件夹,src代表我们项目的源代码目录,然后在它的同级新建一个index.html文件作为我们将来要去展示内容的地方,然后我们再去src目录里模拟一下开发的需求,新建一个js目录,因为我们要采用的是模块化的开发,在js文件夹下新建一个工具模块utils.js

一个例子告诉你为什么需要webpack 💦

我们在utils.js下定义两个数学方法:

const sum = (m,n) => {
    return m+n;
}
const square = m => {
    return m*m;
}

接下来,我们想要演示一下ES module,我们直接通过export把上边的 sum和square导出:

export {sum,square}

完成以后,我们这样就相当于实现了一个模块。 

 紧接着,我们在src目录下新建一个入口文件 index.js  

 在 index.js 中我们可以使用 import 关键字,因为我们在 utils.js 里是用 export 导出的,然后在入   口文件中我们就可以使用定义的数学方法: 

import  {sum,square} from './js/utils.js'

console.log(sum(10,20));
console.log(square(10));

然后我们稍微梳理一下各文件之间的关系:

我们准备了一个index.html静态页面,在src目录下有我们采用模块化思想去编写的文件,当前我们采用的规范是ES module,接着在index.js入口文件对定义的方法进行使用,这样我们来到index.html里自己手动把js文件进行引入。

后期我们会通过webpack动态的完成这个事情,现在我们先自己写一下:

<script src="./src/index.js"></script>

在浏览器中运行:

报错说明在当前浏览器下没有办法识别我们的 ES module

 解决办法:

<script src="./src/index.js" type="module"></script>

重新刷新页面:

现在就成功的输出了,那是不是说明我们没有必要使用webpack了呢,其实并不是,因为我们在开发当中,由于人员的不同,所采用的规范不一样,可能有人用的是commonjs

我们再进行一下演示,在js目录下新建api.js模拟commonjs规范,采用commonjs方式对它进行导出:

const getInfo = () => {
    return {
        name:'ace',
        age:40
    }
}
module.exports = getInfo

再在index.js中采用commonjs方式进行导入:

const getInfo = require('./js/api.js')

打开浏览器看看有没有报错:

这里说require是没有定义的,换句话说我们采用commonjs规范之后,我们没有办法在浏览器中使用这一部分的代码,这样规范统一不了,在浏览器中就不能够正常的运行。所以需要有人站出来把这个规范进行统一 。

webpack登场💦

我们直接在项目目录下进行webpack命令调用:

我们可以发现在目录结构里多了一个dist目录,里面有个main.js文件:

webpack会默认去到我们项目下边找src,然后找里面的index.js,再把index.js里面的资源产生依赖图再做一个统一的打包,默认会在项目下边产生一个dist目录,我们打包的代码就都在main.js中了

因为现在是production生产模式,所以代码都是压缩过的,所以看到的就是这样的结果。

我们去index.html里看看我们之前因为模块化规范不一致运行不了的代码,在经过webpack打包后,能否正常的输出 

但是我们忘记没有验证在commonjs里导出的值是否正常可用,所以需要回到index.js入口文件中调用getInfo方法,注意:因为我们修改了入口文件,所以需要再次进行webpack打包

修改后的index.js文件:

import  {sum,square} from './js/utils.js'
const getInfo = require('./js/api.js')
console.log(sum(10,20));
console.log(square(10));
console.log(getInfo());

然后修改index.html,引入main.js,看看打包后的代码能否正常输出:

<script src="./dist/main.js"></script>

输出结果:

前面两个是通过ES module导出的,最后这个是commonjs导出的,所以webpack可以帮我们做不同规范的模块打包的操作,这是我们对webpack的简单了解和应用,后面会对其他的功能和配置进行了解。

三、Webpack配置文件💨

在学习本节之前,我们先对上一节进行一下总结:

webpack会默认找到我们当前项目下边的src文件夹里的 index.js 入口文件。然后把它作为入 口通过依赖进行查找,最终在dist目录下边生成一个 main.js 文件。这个文件里的语法没有进  行处理,我们现在只是证明了 webpack 可以对不同的模块规范进行打包操作。

我们在上一节打包的时候会给一个warning,因为我们没有设置这个mode,后续我们再对他进行单独配置的说明。

webpack局部打包 💦

webpack 打包文件可以使用全局打包或者局部打包的命令,我们在终端上直接输入 webpack 会执行全局的 webpac k进行打包,但是为了多个项目的兼容性,一般都在各个项目上进行局部打包。

我们先创建一个新文件夹webpack-02,在里面和上一节一样进行目录结构的搭建,然后再为当前目录局部安装webpack。 

局部安装webpack操作:

npm init -y

npm i webpack webpack-cli -D

安装完毕后的目录结构:

通过npx调用webpack命令:

npx 会在 node_modules 文件夹里 .bin 目录下 找到 webpack文件

我们在命令行执行这个命令(为什么执行npx不是npm会在后面讲解):

npx webpack

执行完命令后会生成一个dist文件夹,文件夹下的main.js文件就是我们打包后的文件

这样我们就学会了在项目开发过程中,使用局部的webpack对项目整体实施打包。

自定义入口文件名💦

下面我们先删除dist目录,让我们把目光看向src目录下的 index.js ,在之前的学习,我们知道webpack会默认去src目录里找index.js来作为入口文件,那如果我们把他的名字改了呢,webpack该怎么找到他呢?

我们把 index.js 改个名字,改成 main.js ,然后运行 npx webpack命令,结果显而易见会报错。

在命令行中我们就可以添加配置来自定义入口文件名:

我们需要通过 --entry 来进行指定:

npx webpack --entry ./src/main.js

运行完后,dist目录和 main.js 文件都正常产出了,这样我们就成功的自定义了打包入口

自定义输出目录 💦

我们成功实现了自定义入口文件名,那输出的目录能否也可以自定义呢,答案显然是可以的 

同样,我们依然是在命令行中添加配置来自定义输出目录:

我们需要通过 --output-path 来进行指定:

npx webpack --entry ./src/main.js --output-path ./build

运行完后,这把输出的目录就不是 dist 了,就是我们定义的 build 了,里面仍然是 main.js

通过package.json自定义配置💦

在之前的学习中,不论是自定义入口文件名还是自定义输出目录都是在命令行里进行配置的,这样写起来是非常麻烦的,还有一种更加简便的方法,webpack允许我们利用相应的模块导出一些具体的配置项。

在 package.json 中我们可以配置一些短命令来简化我们的使用

我们试着把自定义输出目录这一节里在命令行中进行配置的命令在 package.json 里进行配置,在这里可以添加一个 build 选项,它的具体命令我们把原来命令行的命令复制一下,注意别把 npx 复制上了,把复制的命令粘贴到 build 项的值里。如下面代码所示:

"scripts": {
    "test": "echo \"Error: no test specified\" && exit 1",
    "build":"webpack --entry ./src/main.js --output-path ./build"
  },

然后在命令行中执行你配置的选项就行:

npm run build

运行完后,同样会生成一个 build 目录,里面有main.js文件。

npm与npx的区别💦

这里可能有些小伙伴会问,为啥这里是 npm ,之前是 npx 呢?下面我们进行一个简单的介绍:

npm 是Node.js的软件包管理器,我们可以在package.json文件中为项目指定所有依赖项(软件包),当需要为其安装依赖项时,只要运行npm install就可以。

npm 本身不能够执行任何包,对于本地项目的包,如果想要执行,则需要写入到 package.json 里面,然后通过 npm 来解析 package.json 文件,解析到包的 bin 文件路径,在 bash 中执行。
 

npx是一个工具,是一个npm包执行器, 它是一个简单的 cli 工具,来让我们更加方便的执行一些 npm 包,而不用通过 npm 来将包安装到开发者的电脑上面。

npx的主要特点:

  1. 临时安装可执行依赖包,不用全局安装,不用担心长期的污染。
  2. 可以执行依赖包中的命令,安装完成自动运行。
  3. 自动加载node_modules中依赖包,不用指定$PATH。
  4. 可以指定node版本、命令的版本,解决了不同项目使用不同版本的命令的问题。

通过webpack.config.js配置💦

这里默认名字就是 webpack.config.js,后面我们再讲如何自定义这个名字,在webpack.config.js里我们可以导出具体的配置项。

在里面我们进行两个常见的配置,entry 是我们入口文件的路径,output 定义输出文件的路径,默认情况下设置为dist目录 ,这个我们当然可以自己修改。filename是打包的结果文件的名称,path是 build.js 的路径。

module.exports = {
    entry:'./src/index.js',
    output: {
        filename: 'build.js',
        path: './dist'
    }
}

然后我们再去package.json里对他进行一些简化,因为我们不需要在命令行中设置具体的配置参数了,所以把 build 项设置成这样:

"build":"webpack"

然后在命令行中我们还是执行这个命令:

npm run build

然后报错了说output里的path不是一个绝对路径:

这是我们需要特别注意的一点,对于entry是可以采用相对路径的,但是对于output里的path就必须是一个绝对路径。

nodejs下的path模块可以设置绝对路径,然后直接调用它,它会把一个路径或路径片段的序列解析为一个绝对路径,__dirname是一个成员,用来动态获取当前文件模块所属的绝对路径,也就是你项目的根目录。

const path = require('path')

module.exports = {
    entry:'./src/index.js',
    output: {
        filename:'build.js',
        path: path.resolve(__dirname,'dist')
    }
}

整体意思就是,我们要去项目下边新建一个dist目录,然后把打包文件的名称命名为build.js,入口就是src目录下的index.js 

重新执行 npm run build 看看能否成功:

执行完毕后,成功生成dist目录,目录下是我们打包后的文件 build.js

总结 💦

我们首先第一个步骤是使用了全局的webpack进行打包,然后我们发现可以在命令行里面使用局部webpack,还可以在命令行里做一些参数的配置,但是我们觉得参数命令太长了,非常麻烦,所以可以直接配置一个短命令放在package.json当中。写完之后,我们又考虑到以后可能有更多的配置项需要去自定义,然后我们知道了webpack也会去提供具体的配置文件的方式给我们使用,这样就有了webpack.config.js。这里我们要注意的是入口采用的是相对路径,而输出采用的是绝对路径。这些就是webpack配置文件的一些简单上手。

四、Webpack依赖图💨

在打包的过程中我们会遇到一个概念叫 Webpack依赖图

当前我们的前端开发基于模块化的思想,例如我们有个login.js,它在工作的时候可能有一些资源文件比如用到某张图片 lg.png,可能会有自己的样式 login.css,如果我们想要对它直接进行部署就期望能够统一到一个静态资源里面。

因此webpack就会设计一个入口文件,这里就是src目录下的index.js文件,所以我们就可以在index.js当中通过相应的语法比如使用 require 和 import,可以导入其他的模块,当然这些其他的模块不仅仅只限于js文件,因为在webpack眼里一切皆模块。

我们可以通过不同的loader(这块后续章节会讲)来对里面的内容做转换,当前我们是为了突出依赖关系,比如说我们在index.js之中引入了login.js,然后在login.js中我们可能会用到login.css,这样就有了层级关系。我们先在index里面找到login,再在login里面找到css,这样整个依赖关系里的所有内容都经过具体处理后,再产出为我们之前看到的build.js(也就是打包后的文件)

我们回到本文第二节Webpack上手的项目中,通过我们第三节webpack配置文件学到的知识,对package.json 和 webpack.config.js对项目进行配置,然后执行打包。

下面是打包后的项目目录结构:

那回到我们本节的主题,为了体现这个依赖图的关系,我们在 js 目录下新建一个 xj.js 文件。为啥老是拿js举例子呢,因为现在咱还没学处理其他文件类型的 loader,所以我们目前就看webpack默认就能处理的js文件先。

xj.js 文件中执行一个简单的输出:

console.log('小杰学前端');

下面我们执行 npm run build 对入口文件进行打包,如果在dist目录下生成了build.js就代表打包成功,在 index.html 中对输出文件 build.js 做一个手动的引入:

<script src="./dist/build.js"></script>

然后我们在浏览器中运行,看看输出结果:

为什么我们在 xj.js 中写的文本为什么在浏览器中没有输出呢?

这就是因为我们本节所提到的依赖关系,我们现在找到入口文件 index.js ,可以发现 xj.js 并没有把他引入,也就是说webpack在打包的时候根本不会考虑 xj.js 这个文件。因此如果我们想把这个文件加到打包流程当中,就应该先把这个文件给加到依赖图中,也就是通过 import 找到 js 里面的 xj:

import  {sum,square} from './js/utils.js'
const getInfo = require('./js/api.js')
import './js/xj'
console.log(sum(10,20));
console.log(square(10));
console.log(getInfo());

上面就是我们这个项目的入口文件 index.js。

引入完毕后,重新执行 npm run build 进行打包,再运行浏览器看看输出内容:

现在 xj.js文件里的文本内容就成功输出了,这样我们就明白了所谓的依赖是什么关系,后续我们想让webpack 处理图片,css或者其他的媒体资源,我们应该先把它们加到依赖图中,这样webpack才能找到它们,然后才能通过loader对打包结果和流程进行处理。

现在你对webpack是不是有了一个简单的了解了呢,是否可以用webpack进行一下打包的操作了呢,在后续的文章中,博主还会继续更新webpack的学习文章,由浅入深带你走进前端工程化的大门👰👰👰

 

评论 19
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

Frank.30

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值