百度日志中台前端重构实践

维权提醒:如果你或身边的朋友近五年内因投顾公司虚假宣传、诱导交费导致亏损,别放弃!立即联系小羊维权(158 2783 9931,微信同号),专业团队帮你讨回公道!


                                                                                                                                                <p>日志中台是百度内部针对打点数据的全生命周期管理平台,作为公司日志数据的唯一入口,承担以下核心职能:1.功能覆盖:提供从数据采集、传输、存储到查询分析的一站式服务,支持产品运营分析、研发性能监控、运维管理等多元场景。2.业务赋能:通过标准化流程实现用户行为日志的埋点申请、审批及退场管理,助力APP端、服务端等业务线挖掘数据价值。3.生态协同:与大数据平台、推荐中台、性能平台深度联动,避免重复建设,提升资源利用率,强化业务中台能力。</p> 

01 项目背景

2020年初启动的日志中台前端项目,随着业务发展逐渐暴露出严重问题。整个前端项目技术负债多,有500多个文件,共11万多行源码。项目已经变得老旧而臃肿。面临线上bug频发、排查问题效率低下等各种问题,陈旧的技术栈与低效的流程也制约了团队的生产力。因此需进行全面全面重构,通过基于业务导向的架构优化、开发测试流程规范化,从而提升前端开发效率,使项目具备长期稳健发展的技术基础。本文将重点介绍我在重构项目过程中的一些实践经验。

02 前端项目面临的问题

先介绍下日志中台前端项目的基本情况

  • 核心框架:Vue 2.6 + Vuex 3.1.1 + VueRouter 3.0.6

  • UI组件库:ElementUI 2.15.13

  • 构建工具:@vue/cli-service 3.11.0(基于Webpack 4)

  • 部署平台:测试环境(FIS3)、生产环境(Tower)

下面我将从4个维度来分析下前端项目所面临的各种问题。

2.1 代码质量

由于项目没有接入代码格式化 prettier 和 代码规范检查 eslint,导致项目的代码质量堪忧,各种各样的代码风格并存。在开发需求过程中,各自的编码风格不一致,维护时需额外适应时间,甚至由此引发线上问题。

2.2 基础建设

1. 代码臃肿,维护困难

  • 全项目500+源文件中,30+文件超1000行,5+文件超2000行,最大文件达5000行。

  • 巨型文件导致:

    IDE卡顿(Mac开发时频繁卡住)。

    热更新失效(>2s延迟,大文件需手动刷新浏览器)。

2. 技术栈陈旧

  • 仍使用已停止维护的vue-cli(Webpack 4时代工具链),与现代构建工具(Vite、Webpack 5)存在代差。

2.3 构建和部署

测试环境

测试环境的部署采用的是 fis3,这是百度FE团队早期自研的集构建、部署于一身前端构建工具,日志中台项目使用其部署测试环境的功能。具体流程就是在开发者本地执行打包操作,然后将打包产物通过fix3推送到后端的服务器上去,替换掉之前的打包产物,从而实现部署新版本。

  • 这种方式存在诸多问题:

  • 本地构建依赖不一致,易引发环境差异问题。

  • 无CDN缓存,静态资源直推后端服务器。

  • 无版本管理,存在代码覆盖风险。

  • FIS3已停止维护,社区无支持。

  • 本质问题:前后端未完全分离,违背当前主流协作模式。

生产环境

生产环境的部署则采用的是Tower平台,这是百度内部的线上部署平台,通过平台的形式将master分支的代码在服务器上编译构建,将打包后的产物推送到线上环境对应的服务器上,从而实现完整的上线流程。这种上线方式同样存在诸多不足:

  • 上线耗时长达30分钟,无增量构建能力。

  • 多服务器部署时存在“漂移现象”(请求路由不一致)。

  • 操作流程复杂,平台限制多(如回滚困难)。

  • 仍缺失CDN加速,影响页面加载性能。

2.4 优质组件

在Vue技术栈中,模块和组件的模糊概念,导致很多开发者无法区分其区别。

1. 组件与模块概念混淆

  • src/components目录下堆积40+文件夹,但90%为一次性业务模块(如5个重复封装的Table组件),缺乏真正的复用价值。

2. 基础建设缺失

  • 无通用业务组件库,开发依赖Element UI原始组件。

  • 高频逻辑(如表单校验、数据请求)需重复实现,通过“复制粘贴”开发,导致代码冗余和一致性风险。

03 全面重构拆分

下面是针对以上项目中的各个痛点的重构具体手段。

3.1 接入工程化

前端项目若缺乏统一的代码规范和质量控制,随着业务增长,代码可维护性会急剧下降,最终导致开发效率低下、线上问题频发。因此,引入业界成熟的工程化方案是提升代码质量的关键。

工程化改造步骤

1. 清理冗余配置

  • 移除项目中无用的、过时的配置(如废弃的.babelrc、冗余的webpack配置等),减少干扰项。

2. 统一基础配置文件

  • 在项目根目录下添加必要的配置文件,确保团队开发环境一致:

  • .vscode/settings.json(统一VSCode编辑器配置)

  • .editorconfig(统一缩进、换行等基础格式)

  • .npmrc(设置为百度npm镜像)

  • .browserslistrc(明确目标浏览器兼容范围)

3. 接入代码规范工具

  • Prettier:自动格式化代码,统一风格(如缩进、引号、分号等)。

  • ESLint:检查JavaScript/Vue代码质量,避免常见错误。

  • Stylelint(可选):规范CSS/Less代码风格。

4. 优化开发体验

  • 推荐安装必要的VSCode插件(如ESLint、Prettier、Volar等),提升开发效率。

5. 提交时增量强制校验(Git Hooks)

  • 接入husky+lint-staged,在git commit时自动执行代码检查,阻止不合规代码提交。

配置参考

历史代码修复策略

原则:“自动修复优先,手动修复补充”,避免无限制添加eslint-disableignore规则,导致规范形同虚设。

具体执行步骤

1. 自动格式化(Prettier)

2. ESLint自动修复

3. 分析剩余问题

  • 使用eslint-formatter-html生成报告,评估剩余问题。

  • 调整ESLint规则(如放宽部分历史代码限制),拆解为多个小任务手动修复。

4. 回归测试

  • 联合熟悉业务的同学进行全量测试,确保修复过程不影响系统功能。

效果验证

  • 代码风格统一:所有新提交的代码均符合规范,减少风格争议。

  • 错误率下降:低级语法错误、边界条件导致的JS报错大幅减少。

  • 开发体验提升:IDE卡顿减少(格式化后代码更简洁),热更新效率提高。

3.2 升级基建

3.2.1 源码优化与依赖治理

问题现状

项目存在大量技术债务,包括:

  • 冗余资源(未压缩图片约2M)

  • 无效依赖(22个未使用的npm包)

  • 混合模块规范(require/import混用)

  • 废弃技术栈(如已停止维护的iView)

优化措施

1. 资源优化

  • 使用基于Tinypng封装的工具批量压缩图片,体积减少65%

  • 清理已下架页面的遗留代码(约15个路由)

2. 依赖治理

  • 移除22个无用依赖

  • 统一使用ES Module规范(手动替换require为import)

3. 技术栈升级

  • 替换老旧组件库:vue-json-diff、vue-code-diff、vue-codemirror 替换为 monaco-editor

3.2.2 构建相关

相对于以往的 Webpack 或者 Vue CLI,存在开发服务器启动慢(平均45秒)、热更新延迟高(2.5秒)、构建流程复杂(需Babel转译ES5)。

Vite 配置详见:https://www.yuque.com/shuoshubao/bg00go/wc87bknptk3lomed#wyx0p

接入Vite后,低配置电脑同学开发时的平均热更新时间由2.5秒缩短到100毫秒。在单个需求完成耗时方面,由之前的4.2人天缩减到3.4人天,综合人效提高19%

另一方面,由于 Vue CLI 是基于babel将esnext代码转成es5,而Vite基于esbuild不需要进行降级编译。在将 Vite 的配置 build.target 设置为 [‘chrome100’] 后,甚至连非常新的esnext语法糖都不需要转换,浏览器直接可以使用前端的源码,极大的利用了esnext带来的开发便利,而不需要关注Babel的版本以及各种依赖包和复杂的配置。

3.2.3 部署相关

百度内部主流的部署平台是 Fcnap。这是一个类似Vercel的前端一站式部署平台,基于git分支,只要检测到分支变动,就会触发自动构建和部署。

只需配置好各个测试环境以及生产环境的基本信息,后续在需要开发中,只需要将分支和测试环境关联起来,就可以达到随时提交代码随时部署的效果;上线过程更是丝滑,只需要将代码合到master分支,就会自动上线。

将 fis3 以及 Tower 迁移到 Fcnap 后有如下优势:

  • 测试和生成环境使用一套部署逻辑

  • 上线部署耗时由30分钟缩减至2分钟

  • 提供cdn功能,每次上线后增量更新的静态资源只有500kb

  • 上线期间访问系统不会出现白屏现象

  • 上线过程对用户无任何影响

3.2.4 接口调试

传统开发模式的痛点

在传统前后端协作中,存在典型的”接口依赖症”:

1. 开发阻塞:前端必须等待后端接口Ready才能开始调试

2. 效率低下:联调阶段频繁出现接口变更,导致重复返工

3. 数据不可控:依赖真实测试环境数据,难以覆盖边界场景

数据表明:在接口未就绪阶段,前端开发效率会下降60%以上

真正的”前后端分离”实践

核心原则:开发阶段解耦,联调阶段对接

1. 规范先行

  • 后端通过YAPI等平台提供完整的接口文档

  • 包含:请求方法、参数结构、响应体示例、状态码定义

2. Mock数据要求

  • 真实业务数据(非简单根据接口文档生成各种随机数据)

  • 可自定义异常场景(404, 502等真实场景还原)

  • 支持动态响应(根据参数返回不同数据)

针对这个开发环节,我们也基于Vite实现了一个非常好用的插件:vite-plugin-mock,用于提升开发效率。整体的设计如下:

相比于传统的 mock 方案,vite-plugin-mock在开发体验、数据维护上有更好的开发体验。

特性 传统Mock方案 vite-plugin-mock
数据真实性 随机生成,不可用 可在真实接口数据上任意修改
开发体验 需要启动Mock服务 配置简单,可随时修改数据
联调切换 手动修改请求地址 自动代理无缝切换
数据维护 独立维护Mock数据 数据存放在本地,每个人都可维护单独的数据

3.3 构建体积优化

这一部分主要从以下三个技术方案着手优化,再配合其他人工优化手段,打包体积由开始的 14M 优化到 1.8M,接入cdn功能后,则仅有500kb。

3.3.1 element-ui

fork element-ui 源码, 采用rollup进行打包,优化部分源码,修复部分 bug,重新发包为 @baidu-log/element-ui

这一步骤,js 体积从 1.2M 优化到 500kb。并结合下面 externals 功能,进一步使用cdn功能缓存这部分文件体积。

3.3.2 引入externals功能

将基础包通过cdn的形式在 index.html 模板中引入其umd格式的文件,从而避免打包这部分内容。这部分会用到cdn的缓存功能,会节约掉大约 2M 的体积。

vite-plugin-externals

这个是开源的vite插件,配置也比较简单,详见配置:https://www.yuque.com/shuoshubao/bg00go/wc87bknptk3lomed#LiR2X

vite-plugin-assets

这个是为了配合上面vite-plugin-externals插件,将对应的externals的npm包对应的umd文件插入到模板中,代码详见:https://www.yuque.com/shuoshubao/bg00go/wc87bknptk3lomed#xts88

为什么不直接写在 index.html 里呢?因为像 vue 和 react 这样的框架,在开发时都提供了对应的开发调试工具:dev-tools。而使用 dev-tools 则需要提供对应的 dist/vue.js,而react对应的则是 react.development.js

3.3.3 大包的特殊处理

1. monaco-editor

项目中用到了 monaco-editor 这个编辑器组件,直接打包将会非常大,有10M以上的体积。根据官方提供的方案即可进行如下封装,其中 cdn 地址由百度的 npm 镜像服务提供支持。

代码详见:https://www.yuque.com/shuoshubao/bg00go/wc87bknptk3lomed#gozcq

2. xlsx, fabric 等

在项目中用到了 xlsx, fabric, markdown-it, echarts, draw.io 这几个体积很大的包,但又不属于很基础的包,只有少部分页面的某个功能点才会用到。针对这些包采用从cdn异步加载其umd包的形式来引入,而不是通过 import npm包的形式。

代码详见:https://www.yuque.com/shuoshubao/bg00go/wc87bknptk3lomed#rEBee

以上两种优化方案,与常见的动态引入方案(dynamic import)是有很大区别的,dynamic import 是通过编译工具将对应的npm包打包成一个独立的chunk,然后在使用的时候再通过loadScript方式引入。这种问题在于文件的缓存,一是chunk可能会变,二是像Vercel这种平台,每次发布都是一个全新的 s3 bucket,上线后缓存功能也就失效了。而上述这种方案,则利用npm镜像服务,每次都访问固定的cdn地址,也就达到了cdn的缓存目的了。

3.4 建设组件库

鉴于项目没有优质组件的背景,从零到一搭建了组件库,组件库主要包含以下内容:

1. 基于 Vuepress 建设高质量组件库文档

2. 迁移 element-ui 文档,并修复其中大量劣质示例代码

3. 采用 Vitest 编写工具方法的测试用例

4. 提供9个高频优质通用组件,10个业务组件

组件库文档:https://logsfe.vercel.app/

文档分为以下几大模块

实际效果:组件库中的组件在项目中目前已被使用240次,用户使用体验良好。

3.4.1 通用组件

基于大量的B端系统开发经验,提炼出配置化表格和配置化表单组件,满足项目中90%的开发场景,通过重构部分页面后比较分析,在写对应模块时,能减少40%的代码。

通用组件均与业务解耦,设计优雅的api,并提供大量示例。组件库里只提供少量的优质组件,严格把控每一行提交的代码,并为组件中的工具函数提供符合 JSDoc-style 规范的注释,且通过 Vitest 来编写单元测试。

3.4.2 element-ui 文档集成

在实际工作中,发现 element-ui 文档存在很多问题且早已不维护。

  • 主题与日志中台不符,不利于查看

  • 组件默认size过大,一页都看不了多少示例

  • 右侧没有 toc 功能,不方便快速定位

  • 示例很多写法不优雅,以及很多冗余代码被人机的复制到了项目中

  • 在线调试示例采用的是 codepen 平台,这个平台很慢而且经常挂了

基于以上各种问题,将 element-ui 官方的示例 fork 到组件库中,使用和日志中台一样的主题,并修复上述各种问题。

并使用纯前端来实现了一个完全可用的 codepen 组件使用示例功能。

3.4.3 通用工具库

基于B端系统抽象的实用工具方法集合。在组件库中提供优质的说明文档和使用示例。这个已经发布到npm上,并在多个公司和团队使用。

包括日期处理、数据处理、接口数据格式化、针对element-ui的一些实用封装。目前已在项目中被93个文件使用150次。

项目地址:https://www.npmjs.com/package/@nbfe/tools

04 总结与展望

在频繁的需求迭代过程中,项目迟早会变成臃肿老旧的样子。当开发体验、开发速度、代码质量、项目可维护性、联调测试体验、线上质量等全方位令人举步维艰的时候,就该发起大规模的全面重构了。对每一项重构技术需要深刻掌握,才能掌握重构的深度和保证重构后的项目质量。另外,还定制了很多开发规范和最佳实践指导,但项目中仍存在大量不符合规范的地方,将在未来继续进行全量修复,直到将一个老旧的项目重构到更接近现代化前端项目的程度。

                                                                                </div>



Source link

未经允许不得转载:紫竹林-程序员中文网 » 百度日志中台前端重构实践

评论 抢沙发

  • 昵称 (必填)
  • 邮箱 (必填)
  • 网址
关于我们 免责申明 意见反馈 隐私政策
程序员中文网:公益在线网站,帮助学习者快速成长!
关注微信 技术交流
推荐文章
每天精选资源文章推送
推荐文章
随时随地碎片化学习
推荐文章
发现有趣的