视频笔记来源:【零到全栈】4.2-Vite、npm与前端构建这整个系列
前端构建
使用vite、npm和node.js构建前端
环境搭建
vite是用js实现的构建工具,因此需要有运行js的环境
由于它是一个命令行工具,所以要在浏览器之外运行,这时我们需要node.js
直接从官网下载或者Linux下使用apt安装
npm会跟随node.js一起安装,它是一个包管理工具,安装后在项目中使用npm init -y初始化,初始化后项目根目录中会出现一个package.json,这里记录了用到的包和可以跑的命令,常用的字段有:
- name:项目名称
- version:项目版本
- scripts:自定义命令别名
例如:
1 | "scripts": { |
可以将这几个命令简化为:
1 | npm run dev |
接下来使用npm install -D vite安装vite,其中-D命令符用于非网站依赖的库,即这个包不会随着也没进入最后的网站
类似安装vite这样的第三方包后,项目下会产生node_modules和package_lock.json,前者是安装的脚本,后者用于将每个装的第三方包版本锁定,最后要被提交到git
开发完成后,使用vite preview预览构建,使用vite build构建,将多个文件打包成统一的文件,减少网络传输延迟,并根据文件内容在文件名后生成哈希,防止读取旧的缓存,这部分代码是真正运行的,每次build都会重新生成
git管理
需要提交的文件:
package.jsonpackage-lock.json
不需要提交的文件:
node_modulesdist
npm安装依赖库
之前js使用第三方库都是用import导入第三方cdn地址,但这样不稳定,我们可以使用npm来下载第三方库
使用npm install 库名安装需要的库,这里不需要加-D,表示这个第三方库会跟随项目构建
安装后在import时直接导入包名即可,vite会自动引向对应的源文件
前端开发流程
现代前端通常使用框架开发,框架可以看作管理UI组件的工具/规则,这里以React为例
React的核心是将界面定义为一个个组件组合而成,每个数据、结构、样式和行为都可以是一个组件
对应我们将不用框架的写法称为vanilla
React环境搭建
确保node.js环境已经配置好了,在项目根目录执行:npm install react react-dom
- react是react本身
- react-dom用于让react能把组件渲染到浏览器dom上
下载vite后,需要下载一个vite翻译react代码的插件:npm install -D @vitejs/plugin-react,然后在根目录创建vite.config.js:
1 | import { defineConfig } from "vite"; |
用于将插件挂载到vite中
开启一个项目,只需要使用npm create vite构建框架,根据它的提示选择想要用的框架与js/ts即可
React组件
react定义的组件(jsx文件)存放在src/components/下,定义每个组件该怎么工作,但是它不会自己跑到页面上
需要在src/文件夹下新建一个文件,用于将所有组件挂到html的某个位置,我们称为入口文件,在需要的html文件下引入对应组件以及入口文件,即可使用
规定大写开头的组件是react组件,且若在其他组件中嵌套使用,就不需要特地引入
组件内部可以通过传递参数来定义不同内容,使用花括号定义参数{parameter},这称为组件复用
最后,页面也可以作为组件,统一交给最外面的App.jsx接管,这样就可以不用多个html文件了,这个jsx文件还需要一个main.jsx入口文件挂载到一个index.html文件中,前者在src/下,后者在根目录下
最后构建的结果,是所有jsx文件全被合并为一个js文件,index.html只需要引用该js文件就行
部署
现在的项目使用了React+Vite,不能直接发送给浏览器,我们需要在服务器上准备依赖,并生成dist文件夹,让Nginx指向生成的dist文件夹
但是我们如果想访问其他页面,通过不同路由,会发现出现404,这个问题需要依靠Next.js解决,见下
数据驱动页面
数据和页面分开
之前,页面展示的内容都是写死在控制结构的jsx文件中的,这样修改和寻找都会麻烦一些,我们可以将数据统一管理到一个地方,在src/data/下创建文件,可以在里面定义常量kv用于保存显示的内容,对于做多语言、从API获取数据有很大用处
路由管理
之前的页面切换的逻辑是状态驱动页面,即在app.jsx中用一个变量指定当前在哪个界面,这种管理有一个问题,变量的生存域仅在当前文件,若执行了刷新等操作,可能页面又会跳回最初的默认页面,而且URL全部相同,别人打开也都是默认页面
因此遵循数据驱动页面的逻辑,我们可以在src/route/下创建文件,负责管理路由,修改当前URL,使得页面始终保留在当前
Next.js
存在的问题
浏览器执行文件的逻辑如下:
执行HTML->获取需要的js和css资源->渲染资源
而我们所有的页面都是靠js临时画出来的,导致dist文件夹中只会有一个index.html
因此会出现我们之前提到过的情况:刷新后,没有对应URL的HTML等着执行,js显然获取不到,就没法渲染需要的页面
另外还有两个问题,一个是每次执行HTML获取资源临时刷新,首次加载会相对慢,因为需要获取各种资源;另一个是对SEO不友好,因为搜索引擎爬虫并不会执行我们的js,因此它们获得的都是空白页面,不利于SEO进而不利于我们的页面被人发现
这时我们就需要Next.js,它可以更灵活控制路由,且可以将页面预渲染为HTML
项目结构
Next的项目结构和Vite不同,取消了src文件夹,而是将每一部分都放在了根目录,包括App,components等文件夹
其中,Next会自动根据App下的文件夹结构构建路由,即每个子文件夹都会有一个子路由,其中有对应的page.jsx文件,可以直接调用组件文件夹中对应组件,还会有layout.jsx文件控制样式
另外,对于网站上会动态进行或会更新的组件,我们称为客户端组件,需要在jsx开头显式声明"use client",进而在生成和部署的时候Next会额外向浏览器传一份js文件,保证组件可以动态更新,不需要动态更新的称为服务器组件,只需要发送HTML即可
部署
使用npm create next-app@latest创建项目,根据指令进行即可
写完项目后,使用next build指令构建,构建后还不能直接给服务器,我们还需要常驻跑next start这个服务,它用于客户端组件的动态更新,next端的服务器会根据得到的GET请求按照当前用户身份组织内容,直接渲染HTML并传回去
如果不想要这个功能,在next.config.mjs中添加配置:
1 | const nextConfig = { |
这样项目会放入out/文件夹,让Nginx指向该文件夹的前提下,还需要在try_files后面增加$uri.html
兜底
如果想实现动态内容,需要通过后端API获取