返回开发者新闻

探索未确定的未知问题

2023年5月16日发布者:Andrew Reedy

每天有数十亿用户使用 Meta 的产品生态系统进行社交联系或业务互动。这数十亿用户也希望我们为产品连续不断地加速提供新功能和改进功能。因用户群规模庞大,我们每天需要更改成千上万的代码才能满足上述期望。

不断发布如此大量的产品改进功能可能会导致应用程序运行状况下降,从而导致用户体验下降。在 Meta,我们会采用精密的分层预防工具,以防发布有缺陷的产品改进功能。在发布应用之前,我们使用这些预防工具监控各种产品信号,并检测有没有出现运行状况下降的情况。这些信号反映性能、可靠性(功能和系统)和效率这三方面的状况。这些特性统称为产品的“PRE”。为防止发布有缺陷的功能,开发者首先会在编写代码时收集各种观测和分析跟踪数据。此外,观测和监控工具会收集预生产环境中的产品使用数据。使用人工和自动质量保证工具在这些预生产环境中测试产品。

虽然在进行生产之前采用这些机制可评估代码变更的质量,避免产生不良用户影响,但影响用户的代码变更可能会进入生产环境,继而需要重新进行修改以便再次推出。为降低某个问题影响大量用户的可能性,我们采用不同机制向公众逐步发布代码变更。

在达不到用户预期的功能要求时,我们将此问题定义为“性能倒退”。我们会以“信号”一词表明用户表示有些地方不符合预期。然后通过数据成效分析和检测代码,尽快收集有关性能倒退的信号,并通过部署修复方案努力降低对用户的影响。在这些情况下,如果使用工具收集不到强有力的信号,我们将依赖用户报告来收集有关性能倒退的信号。这些报告是通过各种机制获取的,比如用户会摇晃手机来报告问题,表明在遇到问题时他们在应用程序中处于何种情境下。

为确保满足客户需求,并且尽快实现(有时在当天内就需要达成需求),Meta 大力投入了各种可靠性计划和系统,以增强大规模响应能力。

信号可能源自公众用户(个人、公司、团体等)或内部用户。我们会仔细审查内部用户的信号,旨在帮助预防不理想的代码变更进入生产环境。请注意,信号是汇总数据;例如,每一百万用户遇到的漏洞数量也是信号之一。信号也可能源自自动测试工具和方案、开发工具(警告开发者应用存在可能导致运行时问题的代码变更)、系统日志以及其他来源。我们还会使用工具处理这些信号,以便迅速找到原因和相应的修复方案。

在发现性能倒退的情况后,我们接下来会迅速找到相关工程师,以应用并发布修复方案。根据性能倒退的复杂程度,我们会通过许多方法(包括利用 Meta 在机器学习方面的敏锐度)精准确定合适的工程师。鉴于机器学习的工作原理,这是一个持续的过程,我们需要随着新功能的发布再次训练模型,这样才能跟上不断变化的形势。

而这一切并非漫无尽头,我们从检测到性能倒退的情况,到缓解这些情况,以至预防及以可持续的方式遏制情况,一步步地取得进展。在此过程中,我们充分提高了响应能力、投资回报和效率。

在下一节中,我们将详细介绍如何确定已出现性能倒退问题,以及在知道此情况后如何响应。

将未知问题转变为已知问题并进行量化处理

未知问题主要是指用户或系统遇到的缺陷。首先,我们可能会通过许多不同的来源了解可能存在的缺陷。

  • 测试应用程序以及这些应用程序中特定产品是否正常运行的综合测试。
  • 通过测试以找到缺陷的内部用户,其中包括我们的专属测试团队,或 Meta 庞大的用户群。
  • 在应用中遇到问题后通过问题报告对话框报告问题的外部用户。

在有人实际提出这类漏洞,表示有用户遇到有关事件之前,这些漏洞都是未知问题。当这类漏洞报告的数量达到一定阈值时,我们便确定此为实际问题,反映真的出现了性能倒退的状况,也就是代码变更带来了新的漏洞,而我们必须迅速缓解有关影响。报告的主要类型分为以下两类:

  • “已确定的未知问题”- 即检测代码检测到性能倒退问题并加以报告;我们可使用许多工具帮助生成此信号
  • “未确定的未知问题”- 即内部人员找不到性能倒退问题,而我们需要依赖用户报告性能倒退问题

此外,性能倒退还涉及多个类别,比如是出现了代码缺陷、类似垃圾信息的问题,还是存在违反内容政策的一些其他问题。我们的重点是第一个领域,希望解决与代码相关的用户体验问题。面对用户报告的成千上万的问题,如何做到这一点?

生成信号和成效分析

为管理大量报告,我们通过生成特定信号来标记问题。对于第一种信号,我们可通过适当调整的阈值,让该信号告知我们确实发生了事件或性能倒退问题。请注意,根据性能倒退的类型,发生的事件可能不止一件。例如,因使用通用代码库,性能倒退问题可能影响多种产品。我们需要寻找这种共同点,并将其作为单一事件来解决,从而以最优方式调整资源。下图正是一个例子,说明了我们可以如何直观地看出偏离趋势线的情况,这一偏离正表示出现性能倒退的问题。

然后,我们需要收集更多信号,其中某些信号将指示我们可能遇到的性能倒退的类型。这些信号由为特定 Meta 产品调整的机器学习算法生成,可帮助我们了解与性能倒退相关的表现。这些算法可分析用户报告,以确定造成性能倒退的原因,进而判断哪支工程团队可通过部署代码修复方案或其他措施最好地解决问题。

此外,我们还可根据收集的日志数据生成其他信号。这些诊断日志可以是客户端或服务器端日志,其中收集的内容均经过用户同意,可帮助确定问题原因。我们会在应用程序中加入适当的征求用户同意的流程,以确定是否可以根据用户权限收集此类数据。我们还会明确表明对这些数据的保留时间,以令数据收集符合适用法规要求。

通过使用不同的信号,我们可以整理性能倒退问题,并将其分配给适合的产品团队,以便迅速缓解问题影响,使用户体验达到用户预期。

成效分析也源自总体调查结果。我们会审视数据以找到共同的根本原因,并确定是否需要更改代码,以防再次发生性能倒退问题。审视数据是找到可靠方法解决用户体验问题的关键,这样有助于最大限度地逐渐缩小性能倒退的影响面。

我们的移动应用程序不仅包含支持用户报告问题的导航路径,还提供通过摇晃设备表明出现问题的功能。这样,我们就可以收集情境遥测数据。应用发出的黑匣子信号还可进一步丰富遥测数据。黑匣子与飞行记录器相似,可自动获取有关报告缺陷时应用程序出现什么问题的某些日志数据(在用户同意的情况下),以便我们可以更好地诊断问题。

此类遥测数据都将被组合到一组时间轴视图中,以帮助工程团队确定造成问题的原因。考虑到应用的快速发布节奏,以及服务器端应用程序组件的不断变更,如果不使用此功能,我们很难确定问题。随着时间的推移,这些遥测数据有助于我们检测性能倒退的模式,以防止未来发生这些问题。

扩大范围,以涵盖较小的产品影响面

在改进提高信号准确性的功能后,我们可以从容应对更大的性能倒退影响面,其中部分影响面是以前无法检测到的。影响面是指产品中的特定项目,比如动态消息或 Reels。这是一个挑战,毕竟产品不仅包含许多精细的功能,还会定期引进新功能。因此,性能倒退的影响面不仅大,还会逐渐扩大。我们必须不断调整防御和进攻策略。

为调整策略,需要满足以下几个条件:

  1. 必须确定现有产品影响面的准确范围和相应分类
  2. 必须缩减现有产品的性能倒退影响面(可理解为预防)
  3. 必须将我们的算法扩大至新产品的影响面

如果不满足以上条件,我们就得冒险面对因规模、复杂性和不精确性而无法管理的庞大系统。因此,我们不但要维持这种平衡,还得高效管理日常运营。

从解决漏洞到预先防范

我们在继续缩减性能倒退影响面而又不放松防御的同时,还需要更多地关注预防和可用性等其他重要领域。

与预防相关的重点如下:

  1. 如何从先前的性能倒退事件中吸取经验教训?
  2. 我们需执行哪些防御措施才能让这些性能倒退事件不再发生?
  3. 如何确保性能倒退影响面随时间持续缩减?

如前所述,我们需要从先前的性能倒退事件中收集数据,从中吸取经验教训。根据这些经验教训,可以采取以下措施:

  1. 仍然在预生产环境中将标记置于代码中,以便日后提醒我们,这样可阻止不理想的代码变更进入生产环境
  2. 扩大各个层级的测试覆盖范围,以便检测此类性能倒退事件
  3. 更改产品本身以解决这些问题

预防措施可帮助我们在开发周期中尽早发现性能倒退问题,从而不断降低成本。为此,我们需要在开发过程中更早取得充足的信号,从代码编写时和预生产版本的发布周期就要开始搜集信号。这样,不仅可以改善用户体验,还可以降低开发成本,并且有助于将资源分配给新产品开发项目。

增强更高效地处理性能倒退问题的能力后,我们可以更多地关注给用户造成困惑或可用性方面的问题。这些问题的价值更高,其侧重点是改进产品,而非修复产品。随着时间的推移,相较于性能倒退问题,可用性问题的比例应该要有所提高,而可用性问题和性能倒退问题的总数量应该要有所减少。

最终,我们提供的用户体验将随着功能性和可用性的提高而不断改善。

本文是与 Meta 技术项目经理 Bijan Marjan 合作撰写。