前端工程化
什么是前端工程化?
前端工程化是针对现代 Web 开发复杂性不断提高而提出的一种开发理念与实践方法。它将软件工程的原理、技术和工具应用于前端开发过程中,旨在通过
规范化
、模块化
、自动化
和组件化
等手段提升开发效率
、保证代码质量
,并降低维护成本
。总之就是,不停地改良前端项目的开发流程,让开发者能够更高效地开发、更好地进行团队协作、让代码的风格标准化、对资源做压缩以及懒加载、更好地交付部署
一开始,网页页面并不复杂,只是提供一些简单的展示和交互的静态页面,甚至不需要后端。
后来需要根据不同用户返回不同的页面信息,此时我们会用后端读取数据,配合一些模板引擎,在后端拼接好内容再返回,这就是所谓的服务端渲染(SSR)。
再后来,页面变得非常复杂,于是出现了前后端分离,前端被单独拎了出来,专门写 html、css 和 js,变成了 单页面应用(SPA)。但复杂也带来了很多问题,比如多个脚本的执行时机不对、css 名冲突、文件过于臃肿、错误的缓存导致没能下载最新的资源,等前端复杂后出现的一系列问题。
随着 Nodejs 的诞生,我们可以用 JS 去写前端工具了。为了解决上面这些问题,前端界出现了一大堆的工具和框架:Gulp、Angular、babel、Sass、React、Vue、Webpack、Yarn、TypeScript、ESLint、Docker、k8s 等等
前端工程化-模块化
JS 的模块化
将代码做了拆分,解决全局变量污染、依赖关系不清晰、多人协作不方便、脚本引入顺序、单元测试等问题
采用 CommonJS、AMD、UMD 或 ES6 的 import/export 机制实现代码模块化,增强复用性和可维护性
CSS 的模块化
通过 CSS Modules、CSS-in-JS、Vue 特有的 CSS Scoped 等方案,将 CSS 模块化,避免样式表中的全局命名冲突问题
借助 CSS Modules 或其他预处理器(Sass, Less)避免样式表中的全局命名冲突问题
HTML 的模块化
html 通常是动态的,在服务端我们会使用模板引擎(template),将得到的数据注入到占位符中。在后端 Nodejs,我们可以用 pug(曾用名 Jade)、handlebars、ejs 等。
前后端分离后,我们通常使用的是 Vue 的 template(类似 handlebars 语法)以及 React 的 JSX。
Web Components 是 W3C 标准,允许开发者创建可重用的、自包含的 UI 组件。通过
<template>
标签定义组件结构,使用 customElements.define()注册定制元素,并利用 Shadow DOM 实现样式和内容的封装隔离资源整合模块化
解决不同类型的资源无法组织在一起问题,比如 JS 引擎能识别引入的 js 文件,但无法识别 css 文件
使用 Webpack、Rollup 等构建工具,可以将 CSS、JavaScript 以及图片等资源进行模块化处理,并且合并、压缩、按需加载等优化
比如图片,它可以先变成一个静态资源服务的一个资源,然后在 js 文件 import 的时候在转换为一个 url 字符串,或者直接就变成一个 base64 字符串
前端工程化-组件化
解决
原本的以资源类型为单位进行组织的管理
(所有 JS 文件放一个文件夹、CSS 同理),维护困难
,不好复用
的问题组件化是
UI 层面上的更细粒度的拆分
,一种类似 div 等原生元素的 “自定义元素”。组件有自己的 HTML、CSS 和 JS
,同时有自己的状态,并支持嵌入到其他组件中并接受外部的数据,可以进行复用。组件化可以看作是 UI 层组织方式的一种模块化。目前主流的 React、Vue 或 Angular 等框架构建可复用、易维护的 UI 组件,遵循 DRY 原则,降低代码重复度。
前端工程化-规范化
编码规范
:通过工具如 ESLint 统一团队的编程风格和格式。构建流程标准化
:利用 Webpack 或 Rollup 等构建工具设定清晰的编译、压缩、打包、部署等流程。项目结构合理化
:建立合理的目录结构,便于组织和管理不同功能模块的源码git 工作流
: git hook、commitlint 工具等- 其他:
目录结构规定。
代码风格(包括 JS、HTML、CSS)。
注释规范。
Code Review。
请求接口规范。
前端工程化-自动化
重复的可以自动化的流程化工作
,应该尽量去自动化。让人去做,对人是一种折磨,然后也不能保证质量,因为通常流程也很复杂,即使是简单,做多了也容易错自动化构建:配置持续集成/持续部署(CI/CD)流程,确保每次代码提交后自动执行构建、测试和部署任务。工具有 Jenkins、GitLab CI/CD、GitHub Action、Docker(发布制品) 和 k8s(容器编排)等
自动化测试:编写单元测试、集成测试以及端到端测试脚本,保证代码质量和应用稳定性。
脚手架工具:通过 Yeoman、Create React App 等工具快速生成项目模板,简化初始化过程并提供最佳实践。
前端工程化-其他
概念 | 描述 |
---|---|
Babel | 开发时使用高版本 ES 语言特性,通过 Babel 转换为低版本(如 ES5)兼容代码。打包工具内部集成使用 Babel 进行编译转换。 |
tsc | TypeScript 编译器,不仅支持将 TS 编译成 JS,还能够编译为指定的 JS 版本,以实现跨环境兼容性。 |
Polyfill | 对于低版本浏览器不支持的新 API,提供模拟实现的库,例如 core-js,使旧版浏览器也能使用部分新特性。但有些语言层面上的新特性无法 polyfill。 |
Monorepo | 将多个项目放在一个 Git 仓库中管理,方便共享和维护公共依赖,采用 Lerna、Yarn Workspaces 等工具进行统一构建发布。 |
异常监控 | 当前端发生错误时,通过 Sentry 等服务收集并上报异常信息,结合 SourceMap 可精准定位到源码中的错误位置。 |
制品库 | 使用 Nexus 部署私有制品库,用于存储和分发不同类型的制品资源,包括 Docker 镜像、npm 包等,并与 CI/CD 流程配合。 |
VSCode Snippet | 在 VSCode 中自定义代码片段,简化常用或复杂模板代码的编写,提高开发效率,属于自动化开发的一部分。 |
Mock | 在后端接口未完成时,通过 YAPI 等平台创建虚假数据模拟接口返回,便于前端独立调试和开发。 |
单元测试 | 以模块为单位进行逻辑验证测试,确保代码功能正确无误。Jest 是一种流行的单元测试库,在提交或合并代码前执行测试用例。 |
热重载 | 在开发过程中实时监测代码变更,并自动重新编译受影响的模块,无需刷新整个页面即可查看更新结果,提升开发体验。 |
组件库文档 | 使用 Storybook 创建组件库的交互式文档展示,Vue 组件也可选用 Vue Press 构建文档系统,便于组件的管理和复用。 |
Tree shaking | 在打包阶段移除那些虽然被导入但实际并未使用的模块,优化输出文件大小,Webpack 和 Rollup 等打包工具支持此特性。 |