使用构建机器人

为了断言 开发和维护分支 中没有回归,Python 有一组用于持续集成的专用机器(称为构建机器人构建工作器)。它们跨越许多硬件/操作系统组合。此外,每台机器都托管几个构建器,每个活跃分支一个:当将新更改推送到公共 GitHub 存储库 上的此分支时,所有相应的构建器都会安排尽快运行新的构建。

构建机器人运行的构建步骤如下

  • 签出触发构建的变更集的源代码树

  • 编译 Python

  • 使用 严格设置 运行测试套件

  • 清理构建树

作为核心开发者,您有责任在将更改推送到存储库后检查自动构建结果。因此,了解这些结果的呈现方式以及如何解释和诊断各种类型的故障非常重要。

遇到问题时

请仔细阅读此页面。如果您在此处找不到问题的答案,并且需要构建机器人的帮助,获得帮助的一个好方法是

  • 联系 python-buildbots@python.org 邮件列表,其中所有构建机器人工作器所有者都已订阅;或

  • 联系您遇到问题的分支的发布经理。

拉取请求上的构建机器人故障

GitHub 上的 bedevere-bot 会在您合并的拉取请求中放置一条消息,如果在稳定的构建机器人工作器上构建您的提交失败。即使乍一看似乎无关,也要注意评估故障。

并非所有故障都会生成通知,因为并非所有构建都在每次提交后执行。特别是,引用泄漏构建需要几个小时才能完成,因此它们会定期完成。这就是为什么您自己能够检查结果也很重要的原因。

检查自动构建的结果

有三种可视化近期构建结果的方法

  • 每个分支的 Web 界面,网址为 https://pythonlang.cn/dev/buildbot/,其中所谓的“瀑布”视图呈现每个构建器的近期构建的垂直概览。如果您对某个构建感兴趣,您必须单击它才能知道它对应于哪些变更集。请注意,构建机器人网页通常加载缓慢,请耐心等待。

  • 命令行 bbreport.py 客户端,您可以从 https://code.google.com/archive/p/bbreport 获取。安装它很简单:只需将包含 bbreport.py 的目录添加到您的系统路径,以便您可以从任何文件系统位置运行它。例如,如果您想显示开发(“main”)分支上的最新构建结果,请键入

    bbreport.py -q 3.x
    
  • 构建机器人 https://buildbot.python.org/all/ 上的“控制台”界面。这最适合在宽高分辨率显示器上使用。单击彩色圆圈将允许您打开一个新页面,其中包含有关该特定构建的任何您感兴趣的信息。您还可以通过单击顶行中的构建器状态气泡来访问构建器信息。

如果您喜欢 IRC,那么在 irc.libera.chat 上打开 IRC 客户端并加入 #python-dev-notifs 频道会很有用。每当构建器状态发生变化(上一次构建通过,而这一次没有通过,或反之亦然)时,都会向该频道发布一条消息。在推送变更集后关注该频道是一种简单的方式,可以收到通知,了解您应该关注的内容。

一些构建机器人比其他构建机器人快得多。随着时间的推移,您将了解哪些构建机器人可以在构建后产生最快的结果,哪些构建机器人需要最长的时间。

此外,当在同一分支中快速连续推送多个变更集时,通常会为所有这些变更集安排一次构建。

稳定性

构建机器人的一个子集被标记为“稳定”。在进行新版本时会考虑这些构建机器人。规则是,在发布版本时,所有稳定的构建器都必须没有持续的故障。至关重要的是,核心开发人员应尽快修复他们在稳定构建器上引入的任何问题。

但这并不意味着可以轻视其他构建器的测试结果。其中一些构建器已知存在平台特定的问题,这些问题会阻止某些测试成功(甚至根本无法终止),但通常不应引入其他故障。

依赖于标志的故障

有时,虽然您在提交之前已经运行了整个测试套件,但您可能会在构建机器人上看到意外的故障。此类差异的一个来源是,是否已将不同的标志传递给测试运行器或 Python 本身。要进行复制,请确保您使用与构建机器人相同的标志:只需单击失败构建的测试的stdio链接即可找到这些标志。例如

./python.exe -Wd -E -bb  ./Lib/test/regrtest.py -uall -rwW

注意

运行 Lib/test/regrtest.py 与运行 -m test 完全相同。

依赖于顺序的故障

有时故障甚至更加微妙,因为它依赖于运行测试的顺序。构建机器人随机化测试顺序(通过对测试运行器使用 -r 选项)以最大程度地提高在库模块之间进行潜在干扰的可能性;缺点是它会导致看似零星的故障。

--randseed 选项可以轻松地复制给定构建中使用的确切随机化。同样,打开失败测试运行的 stdio 链接,并检查测试输出本身的开头。

为了举例说明,我们假设输出以以下内容开头

./python -Wd -E -bb Lib/test/regrtest.py -uall -rwW
== CPython 3.3a0 (default:22ae2b002865, Mar 30 2011, 13:58:40) [GCC 4.4.5]
==   Linux-2.6.36-gentoo-r5-x86_64-AMD_Athlon-tm-_64_X2_Dual_Core_Processor_4400+-with-gentoo-1.12.14 little-endian
==   /home/buildbot/buildarea/3.x.ochtman-gentoo-amd64/build/build/test_python_29628
Testing with flags: sys.flags(debug=0, inspect=0, interactive=0, optimize=0, dont_write_bytecode=0, no_user_site=0, no_site=0, ignore_environment=1, verbose=0, bytes_warning=2, quiet=0)
Using random seed 2613169
[  1/353] test_augassign
[  2/353] test_functools

您可以使用以下内容复制完全相同的顺序

./python -Wd -E -bb -m test -uall -rwW --randseed 2613169

它将运行以下序列(为简洁起见已进行修剪)

[  1/353] test_augassign
[  2/353] test_functools
[  3/353] test_bool
[  4/353] test_contains
[  5/353] test_compileall
[  6/353] test_unicode

如果这足以在您的设置上复制故障,那么您可以对测试序列进行二分查找,以查找导致故障的特定干扰。将测试序列复制并粘贴到文本文件中,然后使用测试运行器的 --fromfile(或 -f)选项来运行该文本文件中记录的确切序列

./python -Wd -E -bb -m test -uall -rwW --fromfile mytestsequence.txt

在上面的示例序列中,如果 test_unicode 失败,您将首先测试以下序列

[  1/353] test_augassign
[  2/353] test_functools
[  3/353] test_bool
[  6/353] test_unicode

如果成功,则执行以下操作(希望会失败)

[  4/353] test_contains
[  5/353] test_compileall
[  6/353] test_unicode

然后,递归缩小搜索范围,直到得到触发故障的一对测试。此类干扰涉及两个以上测试的情况非常罕见。如果是这种情况,我们只能祝你好运!

注意

在诊断依赖于顺序的故障时,不能使用 -j 选项(用于并行测试)。使用 -j 会将每个测试隔离在一个原始子进程中,因此会阻止你重现测试之间的任何干扰。

瞬态故障

虽然我们尝试让测试套件尽可能可靠,但有些测试无法达到完美的可重复性。其中一些测试有时会显示虚假故障,具体取决于各种条件。以下是常见故障

  • 与网络相关的测试,例如 test_poplibtest_urllibnet 等。它们的故障可能源于不利的网络条件或测试代码中的线程同步不完善,后者通常必须在单独的线程中运行服务器。

  • 处理微妙问题(例如线程间或进程间同步或 Unix 信号)的测试:test_multiprocessingtest_threadingtest_subprocesstest_threadsignals

当你认为故障可能是瞬态故障时,建议你等到下一个版本后再确认。不过,即使故障确实偶发且不可预测,也应在错误跟踪器上报告该问题;如果可以通过修复测试的实现或通过使其实现的参数(例如超时)更稳健来诊断和消除该问题,那就更好了。

自定义构建器

在处理特定于平台的问题时,你可能希望在 buildbot 舰队上测试你的更改,而不仅仅是在 GitHub Actions 和 Azure Pipelines 上测试。为此,你可以使用自定义构建器。这些构建器跟踪python/cpython 存储库的 buildbot-custom 短期分支,只有核心开发人员可以访问该分支。

要在自定义构建器上启动构建,请将你想要测试的提交推送到 buildbot-custom 分支

$ git push upstream <local_branch_name>:buildbot-custom

如果另一位开发人员当前正在使用自定义构建器或忘记在完成时删除分支,你可能会遇到冲突。在这种情况下,请确保另一位开发人员已完成,然后删除分支或强制推送(添加 -f 选项)。

获得测试结果后,删除分支

$ git push upstream :buildbot-custom     # or use the GitHub UI

如果你只对特定测试文件的结果感兴趣,我们建议你(当然只是暂时)更改 Makefile.pre.inbuildbottest 子句的内容;或者,对于 Windows 构建器,更改 Tools/buildbot/test.bat 脚本。