Slack如何将端到端流水线构建时间减半

本文详细介绍了Slack开发体验团队如何通过智能缓存策略和条件构建优化端到端测试流水线,成功将构建时间从10分钟缩减至2分钟,并大幅降低云存储成本的技术实践。

在 DevOps 和开发体验(DevXP)领域,速度和效率对工程师的日常工作有着重大影响。今天,我们将深入探讨 Slack 的 DevXP 团队如何利用现有工具优化端到端(E2E)测试流水线。这一优化降低了构建时间,减少了冗余流程,为 Slack 的工程师节省了时间和资源。

问题:不必要的前端构建

对于我们最大的代码仓库之一(单体仓库),Slack 设有一个 CI/CD 流水线,在将代码合并到 main 分支之前运行 E2E 测试。这对于确保 Slack 应用程序的整个技术栈(前端、后端、数据库以及中间的一些服务)的变更得到验证至关重要。然而,我们注意到了一个瓶颈:构建前端代码花费的时间比预期长,而且过于频繁,即使在没有前端相关变更的情况下也是如此。流程分解如下:

  • 开发者工作流:开发者进行更改并推送到分支。
  • 构建过程:构建前端代码(约 5 分钟)。
  • 部署:将构建部署到 QA 环境。
  • 测试:运行超过 200 项 E2E 测试,再花费 5 分钟。

整个过程每次运行大约需要 10 分钟。其中约 5 分钟(一半时间)被前端构建消耗,即使不涉及前端更改也是如此。

考虑到每天有数百个拉取请求(PR)被合并,这些冗余构建不仅耗时,而且成本高昂:

  • 每周数千次前端构建,每次构建在 AWS S3 中存储近千兆字节的数据。
  • 其中一半的构建与上次合并到 main 分支相比不包含前端更改,导致数 TB 的重复数据。
  • 每次构建 5 分钟,给流水线增加了不必要的延迟(每周数千小时)。

解决方案:采用更智能的构建策略与缓存前端资源

为了解决这个问题,我们利用现有工具重新思考了构建策略。

步骤 1:条件性前端构建

我们的第一步是确定是否需要全新的前端构建。我们通过使用 git diff 及其三点表示法来检测更改,识别当前检出分支与 main 分支最新共同提交之间的差异。如果检测到更改,则触发前端构建任务。如果未检测到更改,则完全跳过构建并重用预构建版本。

步骤 2:预构建资源与内部 CDN

当不需要前端构建时,我们从 AWS S3 定位现有的构建。为了提高效率,我们使用仍在生产环境中的近期前端构建。我们将为 E2E 测试提供预构建前端资源的任务委托给内部 CDN。这减少了在每个 PR 上创建新构建的需求,同时仍确保我们在当前资源上进行测试。

挑战:规模化效率

虽然方法看似简单,但将此解决方案扩展到我们的单体仓库时遇到了一些挑战:

  • 识别前端更改:我们的仓库包含超过 10 万个被跟踪的文件。确定是否存在前端更改需要高效的文件跟踪,而 git 仅用几秒钟就处理完毕。
  • 查找预构建资源:每天有数百个 PR 合并到此仓库中,识别足够新的预构建版本需要强大的资源管理。通过使用简单的 S3 存储概念,我们能够平衡新近度、一致的文件命名和性能来管理我们的资源。
  • 保持快速:我们能够在平均不到 3 秒的时间内判断前端构建是否不必要,并找到近期的构建产物。

成果:构建频率降低 60%,构建时间减少 50%

我们的努力取得了回报,带来了显著的改进:

  • 构建频率降低 60%:通过智能重用预构建的前端资源,我们将不必要的前端构建次数减少了一半以上。
  • 每月节省数百小时:减少了云计算时间和开发者的等待时间。
  • 节省数 TB 存储空间:我们每月减少了 AWS S3 存储数 TB。这些重复资源原本会存储一年。
  • 构建时间改善 50%:这是前端 DevXP 团队及其合作团队的第二个主要项目。第一个项目升级了我们的 Webpack 设置,将平均构建时间从约 10 分钟减少到约 5 分钟。本项目将平均构建时间从约 5 分钟进一步降至仅约 2 分钟。两个项目均成功,我们将 E2E 流水线的平均构建时间从约 10 分钟缩短到约 2 分钟:这是年内的一项巨大改进!

两个意外成果:

  • 更可靠和可信的 E2E 结果:我们的测试不稳定性(指尽管没有代码更改,测试间歇性或不一致地失败)显著降低。这一改进得益于优化的流水线、减少复杂前端构建的需求以及一致的资源交付。根据月度测量,我们观察到了测试不稳定性的最低百分比。
  • 重新发现遗留代码:实施此优化需要深入探究多个系统长期未重大修改的遗留代码。这次探索产生了宝贵的见解,引发了关于代码库行为的新问题,并为未来的增强生成了一系列待办任务。

结论:重新思考前端构建效率

通过战略性地利用 git diff 和内部 CDN 等现有工具,我们成功节省了宝贵的开发者时间,降低了云成本,并提高了整体构建效率。

对于其他公司中面临 DevOps 和 DevXP 类似瓶颈的团队,教训是质疑流水线中真正必要的内容并进行相应优化。这个项目带来的改进事后看来似乎显而易见,但在尚未完全失效的系统中,低效之处常常被忽视。在我们的案例中,重新思考我们处理前端资源的方式为组织带来了巨大的成功。

致谢

像这样的项目涉及许多活动部件:复杂的构建和测试流水线、云基础设施、内部 CDN、前端代码的复杂构建系统,以及我们整个系统中现有的自定义设置。它包括用 Python、JavaScript、Bash、PHP/Hack、Rust、YAML 和 Ruby 编写的代码。我们在没有任何停机的情况下实现了这一目标!好吧,几乎是这样。我们的部署流水线有十分钟的内部停机时间,但很快就修复了。

这项工作离不开以下人员的贡献: Anirudh Janga、Josh Cartmell、Arminé Iradian、Anupama Jasthi、Matt Jennings、Zack Weeden、John Long、Issac Gerges、Andrew MacDonald、Vani Anantha 和 Dave Harrington

有兴趣承担有趣的项目、让人们的职场生活更轻松,或者只是构建一些非常酷的表单吗?我们正在招聘!

comments powered by Disqus
使用 Hugo 构建
主题 StackJimmy 设计