Skip to content

优化 UnitTest CI 稳定性:固定 GPU 工作目录、收敛 pytest 路径并隔离 stateful tests#867

Open
Aidenwu0209 wants to merge 2 commits intoPaddlePaddle:masterfrom
Aidenwu0209:codex/unittest-flaky-opt
Open

优化 UnitTest CI 稳定性:固定 GPU 工作目录、收敛 pytest 路径并隔离 stateful tests#867
Aidenwu0209 wants to merge 2 commits intoPaddlePaddle:masterfrom
Aidenwu0209:codex/unittest-flaky-opt

Conversation

@Aidenwu0209
Copy link
Copy Markdown
Contributor

@Aidenwu0209 Aidenwu0209 commented Apr 9, 2026

背景

当前 UnitTest CI 存在一类典型的不稳定现象:

  • 首次执行 pytest ./tests 时出现批量失败
  • 随后执行 rerun 或 --lf 时又通过

结合现有日志和脚本行为,这类问题主要有 4 个风险来源:

  • GPU CI 脚本没有像 CPU CI 一样显式切到仓库根目录,执行行为依赖外部调用方的 cwd
  • pytest.ini 没有固定 testpaths / pythonpath,全量执行和单文件执行的收集、导入语义不够稳定
  • rerun 目前承担了“放行”作用,容易把 first-run flaky 洗成绿色
  • 一些会修改全局状态的测试文件和普通测试混跑,容易造成进程级污染

本次改动

本 PR 只改了 3 个文件:

  • pytest.ini
  • scripts/unittest_check.sh
  • scripts/unittest_check_gpu.sh

主要调整如下:

1. 固定 GPU CI 的工作目录

scripts/unittest_check_gpu.sh 开头补齐:

  • cd /workspace/$1/PaConvert/
  • echo "Current working directory: $(pwd)"
  • requirements.txt / tests 存在性检查

目标是让 GPU CI 和 CPU CI 一样,始终从 repo root 执行,避免路径漂移影响:

  • requirements.txt 安装
  • pytest ./tests
  • tests/apibase.py 中基于 os.getcwd() 的临时文件路径

2. 固定 pytest 的收集和导入路径

pytest.ini 中新增:

  • testpaths = tests
  • pythonpath = tests

目标是让以下行为更稳定一致:

  • pytest tests/
  • pytest 某个单文件.py
  • python -m pytest

同时稳定诸如 from apibase import APIBase 这类测试工具模块导入。

3. 把 rerun 从“放行机制”改成“诊断信息”

scripts/unittest_check.shscripts/unittest_check_gpu.sh 中统一调整为:

  • 首轮 pytest 的退出码决定 job 成败
  • 失败后仍可执行诊断性 --lf rerun
  • rerun 结果不再覆盖首轮失败
  • GPU 侧移除 pytest-rerunfailures--reruns=3

这样做的目的不是让 CI 更容易绿,而是让 CI 说真话,避免把 flaky 问题洗成“稳定通过”。

4. 隔离会修改全局状态的测试文件

在 CPU/GPU 两个 unittest 脚本中,都把以下 5 个 stateful 文件从主套件中排除,并在主套件之外按文件单独执行:

  • tests/test_set_default_device.py
  • tests/test_set_default_dtype.py
  • tests/test_set_default_tensor_type.py
  • tests/test_set_num_threads.py
  • tests/test_set_printoptions.py

原因是这些测试会修改进程级默认状态,不适合和普通测试混在同一个 pytest 进程里跑。

当前执行策略是:

  • 主套件先跑,并 --ignore 上述 5 个文件
  • 然后这 5 个文件逐个单独起 pytest 进程执行
  • 主套件和隔离套件统一汇总退出码

预期收益

  • GPU CI 不再依赖外部入口目录,路径行为更稳定
  • pytest 全量/单文件执行的收集与导入语义更一致
  • first-run 失败不会再被 rerun 掩盖
  • 会修改全局状态的测试文件与普通测试解耦,降低互相污染概率
  • 后续如果仍有 flaky,日志会更容易定位到真实失败点

兼容性与影响

这次改动主要是 CI 行为收敛和稳定性优化,可能带来这些影响:

  • CI 可能会比以前更容易显式失败
  • 原因是以前有一部分失败会被 rerun 掩盖,现在不再掩盖
  • CI 总时长可能会略有增加
  • 原因是 5 个 stateful 文件会在主套件之外单独跑
  • 这次改动优先解决“CI 反馈真实性”和“执行稳定性”,不等同于已经完全修复底层根因

验证

已完成以下直接相关验证:

  • bash -n scripts/unittest_check.sh
  • bash -n scripts/unittest_check_gpu.sh
  • 检查 pytest.initestpaths = testspythonpath = tests 已生效
  • 检查 CPU/GPU 脚本中:
    • GPU cwd 日志已加入
    • test_set_default_tensor_type.py 已纳入隔离列表
    • rerun 已改为诊断用途
    • GPU 已移除 --reruns=3

当前这条 PR 分支相对 origin/master 仅包含这 3 个文件变更,没有混入其他无关改动。

后续关注

如果这版合入后仍能复现 “first-run fail / rerun pass”,下一步更值得继续排查的方向是:

  • tests/apibase.py 中动态执行与临时文件路径逻辑
  • 是否还有其他未识别出的 stateful 测试文件
  • 是否需要进一步做 per-case 临时目录或更强的执行隔离

@paddle-bot
Copy link
Copy Markdown

paddle-bot bot commented Apr 9, 2026

Thanks for your contribution!

@paddle-bot paddle-bot bot added the contributor External developers label Apr 9, 2026
@Aidenwu0209 Aidenwu0209 force-pushed the codex/unittest-flaky-opt branch from a993582 to e11dbfa Compare April 9, 2026 15:03
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

contributor External developers

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant