前端项目整合总结

前言

做过不少同类型的中后台和移动端项目,积累了一些经验和踩过的坑。这篇把共性的东西整理出来,重点讲做得好的、做得不好的、以及值得学的东西。

一、这些项目到底做了什么

总结下来就是三类形态:

Web 中后台——园区管理、企业服务、GIS 一张图。几乎所有页面都是”表格 + 表单 + 图表 + 地图”的组合,业务逻辑围绕审批流、监测数据、视频监控、应急指挥展开。

移动端 APP——与 Web 后台配套的移动端,核心是”看数据、收报警、做审批、巡检打卡”。用 uni-app 一套代码出 H5、安卓、iOS。

做完一堆项目后回头想,它们的本质高度一致:同一套技术能力 + 同一套业务模式 + 不同的地区/客户配置。


二、哪些地方做得好

1. 动态路由权限体系

不是简单的 v-if 控制菜单显隐,而是后端返回完整菜单树 → 前端动态生成路由表 → 注册到 router。核心在 router.beforeEach 里做异步路由注册,配合 Pinia 持久化 token 和菜单数据,刷新不丢。每新增一个客户或角色,前端零改动,后端配菜单即可。

2. GIS 可视化从二维到三维的渐进演进

早期用 OpenLayers 做二维标绘(画园区边界、标注点位),后来接入 Cesium 做三维展示(倾斜摄影、地下管网、模型压平)。两者并存的关键是各自操作独立 DOM 容器、独立数据格式,互不冲突。统一了坐标系转换层,OpenLayers 的投影坐标和 Cesium 的地理坐标之间自动换算。

3. 重依赖分包策略

中后台项目往往同时依赖 Cesium、three、echarts-gl、bpmn-js、xgplayer、tinymce 等重量级库。在 vite 的 build.rollupOptions.manualChunks 里手动分包,每种重依赖拆成独立 chunk;低频功能(exceljs、html2canvas)做动态 import(),只在用到时加载。不做优化时打包 30MB+,分包后主包控制在 2MB 以内。

4. 大屏实时数据方案

B/S 端基于 ECharts 做实时监控大屏,分辨率自适应用 transform: scale 等比缩放 + rem 做基础布局,适配各种屏幕比例。大数据量场景(几千个监测点实时数据)用 WebSocket + 增量更新替代全量轮询。

5. 跨端原生扩展的隔离设计

移动端需要设备上报、后台保活、推送等原生能力。通过 #ifdef APP-PLUS 条件编译集中放在 App.vue 的 onLaunch 中,原生调用和跨端逻辑完全隔离,不污染公共代码。


三、哪些需要改进

1. 技术栈版本碎片化

Vue2 和 Vue3 项目并行存在,部分 Web 后台还在用 Vue2 + Vuex + Webpack。新项目绝不开 Vue2 了,但老项目的迁移需要排期和业务窗口——不能为了升级技术栈而中断线上服务。

2. 重复造轮子严重

人员选择器、部门树、文件上传、地图拾取器……几乎每个项目都写了一遍。当时觉得”独立改起来方便”,但改一个 bug 要同步五六份代码。后续应抽进私有 npm 包统一维护,难点在于组件要足够通用又不能过度抽象——地图拾取器支持”单选/多选/回显/只读”四种模式,props 设计改了三版才定下来。

3. 文档几乎为零

除了 README 里一句 npm install && npm run dev,没有架构说明、目录介绍、环境配置文档。每次拉新项目都靠口口相传。应从 README 强制包含:技术栈、目录说明、本地跑起来的完整步骤、与后端联调的 baseURL 和代理配置。这件事不难,就是一直没做。

4. 依赖不清理

用 depcheck 扫了一圈,发现不少项目里装了但从未引用的包:swiper(所有页面都是列表型)、cropperjs(裁剪功能改后端处理了)、fabric(画布功能已砍),每次 npm install 都白白下载。应该养成习惯:每完成一个大版本用 depcheck 扫一遍,该删的删。

5. 移动端状态管理缺失

早期做的几个 APP 没加 Pinia,全局状态靠 uni.setStorageSync 和组件传参撑着。业务模块一多(报警、巡查、监测点、特殊作业等十几种),数据流就失控了——同一个用户信息可能在三个页面用不同方式存取。应统一接入 Pinia + persistedstate,和 Web 端保持一致。

6. 表格列数爆炸

中后台表格数据量不大(后端分页),但列数和操作多。几十列 + 每行五个操作按钮 + 有些列渲染组件(下拉、开关),DOM 数量直接爆炸。后续加了列配置功能让用户自定义显示列,固定列用 CSS position: sticky 替代组件库的 fixed 模式(后者会渲染多份 DOM)。


四、学到了什么——值得提炼的知识点

前端工程化完整链路

从一个项目里跑通了完整的前端工程化:TypeScript + ESLint + Prettier + Stylelint + Husky + lint-staged。这些工具单独用不稀奇,但串起来、跑起来、团队都遵守,需要一套清晰的配置和规则。

打包优化三板斧

  • manualChunks 手动分包(vue / antdv / cesium / echarts 各自独立 chunk)
  • resolve.alias 统一依赖版本(lodash 和 lodash-es 别共存)
  • 动态 import() 延迟加载低频模块

动态路由 + 权限的完整实现

不是网上教程里”写死几个角色”那种 demo,而是真正落地了:菜单接口 → 路由生成 → 导航守卫 → 按钮权限指令(v-permission)→ 刷新持久化。整个过程涉及 router API、Pinia store、后端接口协议三端的配合。

GIS 坐标系的理解

二维引擎(OpenLayers)和三维引擎(Cesium)的坐标系不同,前者常用 EPSG:3857(投影坐标),后者用弧度/经纬度。做统一转换层时理解了空间参考系统(SRS)和 Proj4 的基本概念,这对后续任何地图相关项目都有用。

组件抽象的度

不是抽得越多越好。一个组件如果为了”通用”加了 20 个 props 和 5 层 if-else,那还不如两个独立组件。抽象原则:对外只暴露必要 props 和 slots,内部封装复杂逻辑;如果某个场景花两行就能改好,就别往通用组件里塞。

uni-app 跨端的真实面貌

跨端不是”写完一次处处能跑”,而是”写完一次,在三个端各调一遍”。H5 端和 APP 端在路由动画、原生导航栏高度、底部安全区、条件编译粒度上都有差异,每个都要测到。真机调试比模拟器靠谱。

项目基线化管理

从”每个项目复制一份改一改”进化到”三层基线”:

层 职责 怎么管
技术基线 技术栈、构建、规范 脚手架固定,不允许随意改
组件基线 ProTable、ProForm、选择器 私有 npm 包统一版本
配置层 地区、地址、功能开关 环境变量注入

五、实际可以聊的话题

把前面的内容梳理一下,日常面试和述职里,下面这些话题都有东西能说。

话题 1:项目体量和技术栈

我做的主要是中后台管理系统和配套的移动端。中后台用 Vue3 + Vite + Pinia + TypeScript + Ant Design Vue,移动端用 uni-app 做跨端。项目做了不少个,但仔细看它们的底层架构是一样的——动态路由权限、GIS 可视化、大屏监控、审批流——只是不同地区和客户的配置不一样。所以后来我把它们抽成了基线,新项目从基线起,改配置就行,不用从头搭。

要点:说明你做的不是”写页面”,而是理解了一个领域的通用架构。

话题 2:最复杂的一个技术点

权限体系。不是简单的登录验证,是完整的路由 + 按钮 + 数据三层控制。后端返回菜单树,前端 router.beforeEach 里动态注册路由,按钮用自定义指令 v-permission 控制显隐。难点在于刷新后路由不能丢——Pinia 持久化存储 token 和菜单,beforeEach 里做懒加载兜底。好处是每新增一个角色,后端配菜单就行,前端不用动一行代码。

要点:讲清”问题的本质是什么”和”你的解决思路”,不要说太细的代码细节。

话题 3:性能优化做过哪些

一个是打包体积优化。项目里同时用了 Cesium、three、echarts、bpmn-js 这些重依赖,不做优化的话打包出来 30 多 MB。我在 vite 的 manualChunks 里把 vue、组件库、Cesium、echarts 各自拆成独立 chunk,低频库做动态 import,最后主包控制在 2MB 以内。

另一个是大屏的实时数据。几千个监测点每秒都在推送数据,全量轮询服务端扛不住。改成 WebSocket + 增量更新,前端只更新变化了的数据点,图表用 ECharts 的 setOption 局部更新而不是整体重绘。

要点:讲数据对比(30MB → 2MB),面试官喜欢有数字的说法。

话题 4:做过哪些技术决策

二维地图和三维场景要不要合并成一个引擎?最开始也想过都用 Cesium——毕竟三维也能看二维。但实际试下来,Cesium 做二维标绘体验很差,加载慢、交互重。OpenLayers 做二维轻、快、API 简洁。所以最后是双引擎并存,封装统一的坐标系转换层处理投影坐标和地理坐标的互转。代价是多维护一个依赖,收益是各自场景都用最合适的工具。

要点:讲 trade-off,说明你不是”查到什么用什么”,而是做过对比和决策。

话题 5:遇到过什么坑

一个是对”组件复用”的理解。早期为了复用,把一个选择器组件抽象得特别通用,props 加了十几个,里面各种 if-else 判断模式。结果用起来到处传参,改一个地方就影响其他地方。后来学到:组件抽象不要贪多,如果两个场景差异大,就写成两个组件,代码重复一点比过度抽象好维护。对外只暴露必要的 props 和 slots,复杂度关在组件内部。

要点:踩坑不可怕,能说清”学到了什么”就行。

话题 6:如果让你重新设计

首先统一技术栈,所有新项目全部上 Vue3,老项目排期逐步迁移。然后抽公共组件包,人员选择器、部门树、地图拾取器这些跨项目重复出现的,进私有 npm 包统一管理。移动端补齐 Pinia,现在有些 APP 还用 storage 硬传状态,业务一多就乱。最后每个仓库强制写好 README——技术栈、目录说明、怎么跑起来、后端联调地址,新人不用靠口口相传。

要点:体现你有复盘和改进意识。

聊项目时的原则

其实讲项目不用提前背稿,项目是你自己做的,本来就能说清。注意几点:

  1. 先讲”做什么”,再讲”怎么做”。面试官先关心你做的什么业务,再说技术细节。
  2. 对比要有数字。”优化后变快了”不如”构建时间从 40 秒降到 8 秒”。
  3. 踩坑是加分项。能讲出”我当时怎么想错了、后来怎么纠正的”,比讲”我搞了三套技术栈”印象深刻。
  4. 别报菜名。技术栈一句话带过就行,重点讲”用它解决了什么问题”。
  5. 诚实说不会的。遇到没做过的,就说”这块没深入过,我的理解是……”,比硬编强一万倍。

六、总结

几个习惯值得长期坚持:

  • 新项目从基线起,不从头搭脚手架
  • 做完一个版本清一次没用上的依赖
  • 重复三次的代码必须抽成公共组件
  • README 写清楚”新人怎么跑起来”
  • 技术选型能少则少,多一套技术栈 = 多一倍的维护成本

项目整合趁早做。等技术债务大到搬不动的时候,再想改就只能重写了。


内容由 AI 生成,仅供参考。本文发布于 码上学习,转载请注明出处。