夜间 CI 测试¶
本文档说明如何在 Ascend NPU 硬件(A2/A3)上针对您自己的 PR 代码触发夜间硬件 CI 测试,而无需等待预定的夜间运行。
背景¶
默认情况下,夜间 CI 测试按固定计划使用预构建的夜间镜像运行。贡献者可以通过结合 GitHub 标签和评论命令,自助地直接针对其 PR 更改触发这些测试。
Note
schedule_nightly_test_*.yaml 工作流未声明 GitHub Actions schedule:(cron)触发器;它们由外部自动化通过 workflow_dispatch 调度。请参阅
CI 工作流触发器与 schedule_ 前缀。
如何触发¶
1. 发表评论¶
在 PR 中发表以下评论之一,以指定要运行的测试。评论本身就会触发工作流——无需标签。
| 评论 | 效果 |
|---|---|
/nightly |
运行全部夜间测试 |
/nightly all |
运行全部夜间测试(同上) |
/nightly test1 test2 ... |
仅运行指定的测试 |
/nightly <tests> --aop_enabled |
运行指定测试并启用 AOP bisect / classify |
Note
只有仓库的贡献者(Triage 角色)和维护者(Write 角色)才能触发 /nightly 命令。如果您没有此权限,请让维护者为您发表评论。您可以在项目的 治理 页面或查看 CODEOWNERS 文件中找到维护者和贡献者列表。
2. 等待结果¶
GitHub Actions 将触发 Nightly-A2 或 Nightly-A3 工作流。只有与过滤器匹配的测试才会被调度,从而节省硬件资源。
PR 运行与计划运行之间的差异¶
| 计划 / 手动调度 | PR 触发 | |
|---|---|---|
| 触发方式 | Cron(每日)或 workflow_dispatch |
/nightly 评论 |
| 被测代码 | 预构建的夜间镜像 | 您 PR 的 HEAD 提交(源码全新安装) |
| 测试范围 | 所有测试 | 可通过 /nightly <names> 配置 |
| vLLM + vllm-ascend | 来自镜像 | 从源码检出并安装 |
| 测试矩阵 | 来自 main 分支的 matrix YAML | 来自 PR 分支的 matrix YAML |
当检测到 PR 运行时(is_pr_test: true),工作流还会:
- 卸载容器中所有现有的 vllm 软件包。
- 从源码检出特定的 vllm 版本以及您 PR 的 vllm-ascend 提交。
- 从源码安装所有依赖。
- 安装
aisbench基准测试套件。
测试矩阵数据来源¶
夜间测试用例集合(其名称、运行器、测试路径、模型配置)在单个数据文件中声明:
该文件以 a2: 和 a3: 顶级键组织(每个 SoC 一个)。在每个 SoC 下,测试按执行形态(single-node、multi-node、double-node、multi-card、accuracy)分组,每个组包含一个 test_config(或 accuracy 的 nightly / pr_only)列表,其条目带有 name 以及下游可复用工作流使用的字段(os、tests、config_file_path、size 等)。
Nightly-A2 和 Nightly-A3 工作流都会在运行时动态读取此文件——工作流 YAML 中没有硬编码的测试矩阵。/nightly <name> 斜杠命令通过遍历 PR 分支中的同一文件来解析名称,因此新添加的条目可以在合入 main 之前先在 PR 上运行验证。
添加新的夜间测试用例¶
要添加新的测试用例(无需修改工作流 YAML):
- 在
.github/workflows/configs/nightly_config.yaml的相应部分下追加一个条目。每个条目至少需要: name:用于/nightly <name>过滤器的唯一标识符os(用于 single-node / multi-card 的 pytest+yaml 测试)或runner(自动推断)tests:(pytest 目录)或config_file_path:(由 YAML 驱动的模型配置)二者之一size(仅 multi-node / double-node)- 添加实际的测试文件(
tests/e2e/nightly/...下的 pytest 模块或tests/e2e/nightly/.../configs/下的 YAML 模型配置)。 - 打开 PR。一旦 CI 通过,您就可以无需合并 PR 即可在真实 NPU 硬件上验证新条目 —— 请参阅下面的 示例。
可用测试名称¶
您可以传递给 /nightly 的测试名称对应于 .github/workflows/configs/nightly_config.yaml 中匹配部分下的 name 字段。下表反映了该文件的当前内容。
A2 工作流(.github/workflows/schedule_nightly_test_a2.yaml)¶
单节点测试(a2.single_node.test_config):
| 测试名称 | 描述 |
|---|---|
test_custom_op_multi_card |
自定义算子测试(多卡) |
qwen3-vl-32b-instruct-w8a8 |
Qwen3-VL-32B-Instruct W8A8 |
qwen3-32b-int8 |
Qwen3-32B INT8 量化 |
Qwen3.5-27B-w8a8-A2 |
Qwen3.5-27B W8A8 |
Qwen3.5-397B-A17B-w4a8-mtp |
Qwen3.5-397B-A17B W4A8 + MTP |
多节点测试(a2.multi_node.test_config):
| 测试名称 | 描述 |
|---|---|
multi-node-qwen3-235b-dp |
Qwen3-235B-A22B,2 节点 DP |
multi-node-GLM-5.1-w8a8-A2 |
GLM-5.1 W8A8,2 节点 |
multi-node-Kimi-K2.5-W4A8-A2 |
Kimi-K2.5 W4A8,2 节点 |
精度测试(a2.accuracy.nightly 和 a2.accuracy.pr_only):
| 测试名称 | 描述 | 范围 |
|---|---|---|
accuracy-group-1 |
Qwen3-VL-8B、Qwen3-8B、Qwen2-Audio-7B 等 | nightly |
accuracy-group-2 |
ERNIE-4.5、Molmo-7B、Llama-3.2-3B 等 | nightly |
accuracy-group-3 |
Qwen3-30B-A3B、Qwen3-VL-30B-A3B 等 | nightly |
accuracy-group-4 |
Qwen3-Next-80B-A3B、Qwen3-Omni-30B-A3B 等 | nightly |
pr-accuracy-group-1 |
gemma-3-4b-it、internlm3-8b-instruct 等 | pr_only |
pr-accuracy-group-2 |
Qwen2.5-Math-RM-72B、Hunyuan-A13B-Instruct | pr_only |
| 测试名称 | 描述 | 范围 |
|---|---|---|
pr-accuracy-group-* 条目仅在 /nightly(PR 触发)运行中执行;计划任务中的 /nightly all 会跳过它们。
A3 工作流(.github/workflows/schedule_nightly_test_a3.yaml)¶
多节点测试(a3.multi_node.test_config,4 节点):
| 测试名称 | 描述 |
|---|---|
multi-node-deepseek-v3.2-W8A8-EP |
DeepSeek-V3.2-W8A8 使用 EP,4 节点 |
双节点测试(a3.double_node.test_config,2 节点,在多节点测试之后运行):
| 测试名称 | 描述 |
|---|---|
multi-node-qwen3-dp |
Qwen3-235B-A22B,2 节点 DP |
multi-node-qwenw8a8-2node-eplb |
Qwen3-235B-W8A8 使用 EPLB,2 节点 |
multi-node-dpsk3.2-2node |
DeepSeek-V3.2-W8A8,2 节点 |
multi-node-qwen-disagg-pd |
Qwen3-235B 分离式 PD,2 节点 |
multi-node-qwen-vl-disagg-pd |
Qwen3-VL-235B 分离式 PD,2 节点 |
multi-node-deepseek-v3.1 |
DeepSeek-V3.1-BF16,2 节点 |
multi-node-deepseek-v3.2-W8A8-EP |
DeepSeek-V3.2-W8A8 使用 EP,4 节点 |
multi-node-glm-5.2 |
GLM-5.1-W8A8,2 节点 |
单节点测试(a3.single_node.test_config):
| 测试名称 | 描述 |
|---|---|
mtpx-deepseek-r1-0528-w8a8 |
MTP-X + DeepSeek-R1-0528-W8A8 |
deepseek-r1-0528-w8a8 |
DeepSeek-R1-0528-W8A8 |
kimi-k2-thinking |
Kimi-K2-Thinking |
qwen3-vl-235b-a22b-instruct-w8a8 |
Qwen3-VL-235B-A22B-Instruct-W8A8 |
deepseek-r1-0528-w8a8-prefix-cache |
DeepSeek-R1-0528-W8A8 前缀缓存 |
deepseek-v3-2-w8a8 |
DeepSeek-V3.2-W8A8 |
glm-4.7-w8a8 |
GLM-4.7 W8A8 |
kimi-k2.5 |
Kimi-K2.5 |
qwen3-235b-a22b-w8a8 |
Qwen3-235B-A22B-W8A8 |
Qwen3.5-397B-A17B-w8a8-mtp |
Qwen3.5-397B-A17B W8A8 + MTP |
Qwen3.5-27B-w8a8-A3 |
Qwen3.5-27B W8A8 |
Qwen3.5-122B-A10B-W8A8-A3 |
Qwen3.5-122B-A10B W8A8 |
DeepSeek-V4-Flash-W8A8-A3 |
DeepSeek-V4-Flash W8A8 |
多卡测试(a3.multi_card.test_config):
| 测试名称 | 描述 |
|---|---|
qwen3-30b-acc |
Qwen3-30B 精度测试 |
qwen3-30b-a3b-w8a8 |
Qwen3-30B-A3B-W8A8 |
qwen3-32b-int8 |
Qwen3-32B-Int8 |
qwen3-32b-int8-prefix-cache |
Qwen3-32B-Int8 前缀缓存 |
Qwen3-30B-A3B-W4A8-llm-compressor |
Qwen3-30B-A3B W4A8,通过 llm-compressor |
Qwen3-30B-QuaRot |
Qwen3-30B QuaRot + eagle3 |
Qwen3-32B-QuaRot |
Qwen3-32B QuaRot + eagle3 |
Warning
A3 资源池的最大并发为 5×16 个 NPU。多节点测试
使用 max-parallel: 2 运行,以避免资源耗尽。在 A3 上运行
/nightly all 会排队大量任务——尽可能优先指定具体测试名称。
示例¶
针对你的 PR 运行所有可用的夜间测试:
仅运行自定义算子多卡测试:
同时运行两个指定测试(每个 SoC 一个):
运行单个精度组(包含其所有模型):
运行单个精度模型(仅运行组中的该模型):
修复问题后重新触发:只需推送一个新提交。synchronize 事件
会重新运行工作流,并自动获取现有的 /nightly 评论——无需
发布新评论。
AOP 钩子(Bisect)¶
在任何 /nightly 命令中添加 --aop_enabled 以启用 AOP 流水线:
启用后,工作流将:
- 捕获测试结果(通过 / 失败)。
- 分类失败是环境相关(网络、基础设施)还是代码相关。
- 二分查找真正的代码失败,以定位问题提交。
这对于夜间回归的自动化根因分析非常有用。
添加新测试用例 — 示例¶
要将 my-new-test 添加到 A3 多卡部分:
- 编辑
.github/workflows/configs/nightly_config.yaml,在a3.multi_card.test_config下追加:
- name: my-new-test
os: linux-aarch64-nightly-a3-4
tests: tests/e2e/nightly/single_node/ops/multicard_ops_a3/test_my_new.py
-
在同一 PR 中提交新的 pytest 文件(
test_my_new.py)。 -
从 PR 触发:
工作流将:
pr_nightly_command.yml读取你 PR 的nightly_config.yaml,并解析my-new-test→ 仅调度 A3。Nightly-A3在main上被调度,但setup-vars会检出你的 PR 提交,并从矩阵中读取新条目。multi-card-tests为my-new-test运行一个矩阵任务,且should_run=true。可复用工作流会检出你的 PR 代码(通过vllm_ascend_ref)并运行你的 pytest。
故障排查¶
我发布评论后工作流没有启动。
- 检查评论是否恰好以
/nightly开头,斜杠前没有前导空格或 其他字符。 - 确认你在仓库中至少具有 Triage 权限;未授权 用户的评论会被忽略。
- 修复问题后重新触发时,只需推送一个新提交——工作流将
自动复用现有的
/nightly评论。
只运行了部分测试,而不是我预期的测试。
- 测试名称区分大小写,并且必须与
.github/workflows/configs/nightly_config.yaml中的name字段 完全匹配(参见上表)。 - 对于 PR 触发的运行,矩阵从你的 PR 的
nightly_config.yaml加载,而不是 main。如果某个名称不在你的 PR 文件中,它不会 被识别,调度将被跳过。 - 在 GitHub Actions 中检查
parse-trigger任务的输出,查看解析后的test_filter值。
工作流使用了计划任务镜像运行,而不是我的 PR 代码。
- 确认工作流是由
repository_dispatch(斜杠命令)触发的, 而不是单纯的workflow_dispatch。pr_nightly_command.yml工作流才是 实际调度schedule_nightly_test_a2.yaml/_a3.yaml的工作流,并且vllm_ascend_ref指向你的 PR SHA。
我新增的测试未被识别。
- 请确认
.github/workflows/configs/nightly_config.yaml下的条目是格式正确的 YAML。name字段为必填项,并且必须在 SoC 的相应部分中唯一。 - 矩阵会从您的 PR 分支加载,因此请确保该文件已提交到发布
/nightly评论的同一分支。
如何获取更详细的日志以定位多节点测试中的问题
- 对于大多数问题,GitHub Actions 的 stdout 弹出日志已经足够(该日志始终表示第一个节点的日志)。
- 如果第一个节点的日志已不足以提供有效的日志信息,请查看您的作业摘要,以下载对应测试的日志归档。该归档包含每个节点的框架侧日志和 plog 信息,结构如下:
本页原文 Markdown:在 AtomGit 查看·内容源自开源项目 vl/vllm-ascend