From 4f8fb78fa442ae65e415b6a86090c9bac8cd0b72 Mon Sep 17 00:00:00 2001 From: Wanli Jiang <35160485+Wanli-Jiang@users.noreply.github.com> Date: Tue, 21 Jul 2026 09:41:41 +0000 Subject: [PATCH] [https://nvbugs/6482297][fix] Parse boolean stage-config fields in test_to_stage_mapping The stage-parsing regex in scripts/test_to_stage_mapping.py only accepted trailing numeric fields in Jenkins stage-config arrays, so the 47 stage entries carrying the runWithSbatch boolean (added by the Slurm test refactor #7176) were silently dropped from the test<->stage mapping, including all DGX_B200-PyTorch-* stages. It also matched commented-out stage lines. As a result, tests listed in l0_b200.yml resolved to no stage and test_cli_functionality failed whenever the seeded sample picked one of them. - Accept true/false fields in the stage-config regex and skip //-commented lines when parsing L0_Test.groovy. - Fix test_backend_filtering_consistency to tolerate tests legitimately listed under multiple backends (e.g. unittest/kv_cache_manager_v2_tests under both tensorrt and pytorch), which the parser fix exposed. Signed-off-by: Wanli Jiang <35160485+Wanli-Jiang@users.noreply.github.com> --- scripts/test_to_stage_mapping.py | 10 +++++++--- tests/unittest/tools/test_test_to_stage_mapping.py | 11 +++++++++-- 2 files changed, 16 insertions(+), 5 deletions(-) diff --git a/scripts/test_to_stage_mapping.py b/scripts/test_to_stage_mapping.py index 04626131b658..24f84c458f51 100644 --- a/scripts/test_to_stage_mapping.py +++ b/scripts/test_to_stage_mapping.py @@ -47,7 +47,7 @@ def _load_tests_file(path: str) -> List[str]: # Regex to parse Jenkins stage configurations from Groovy files -# Matches patterns like: "Stage-Name": ["platform", "yaml_file", split_id, split_count, gpu_count] +# Matches patterns like: "Stage-Name": ["platform", "yaml_file", split_id, split_count, gpu_count, node_count, runWithSbatch] # # Pattern breakdown: # "(?P[^"]+)" - Captures stage name in quotes (group 'stage') @@ -56,10 +56,12 @@ def _load_tests_file(path: str) -> List[str]: # "[^"]+" - Matches platform string in quotes (ignored) # ,\s* - Matches comma with optional whitespace # "(?P[^"]+)" - Captures yaml filename in quotes (group 'yml') -# (?:,\s*\d+)* - Matches zero or more comma-separated numbers (split_id, split_count, gpu_count) +# (?:,\s*(?:\d+|true|false))* - Matches zero or more comma-separated numbers or +# booleans (split_id, split_count, gpu_count, node_count, runWithSbatch) # \s*\] - Matches closing bracket with optional whitespace _STAGE_RE = re.compile( - r'"(?P[^"]+)"\s*:\s*\["[^"]+",\s*"(?P[^"]+)"(?:,\s*\d+)*\s*\]') + r'"(?P[^"]+)"\s*:\s*\["[^"]+",\s*"(?P[^"]+)"(?:,\s*(?:\d+|true|false))*\s*\]' +) def _extract_terms(entry): @@ -85,6 +87,8 @@ def _parse_stage_mapping(path): yaml_to_stages = defaultdict(list) with open(path, 'r') as f: for line in f: + if line.lstrip().startswith('//'): + continue m = _STAGE_RE.search(line) if m: stage = m.group('stage') diff --git a/tests/unittest/tools/test_test_to_stage_mapping.py b/tests/unittest/tools/test_test_to_stage_mapping.py index 29052059259a..f8689ff12398 100644 --- a/tests/unittest/tools/test_test_to_stage_mapping.py +++ b/tests/unittest/tools/test_test_to_stage_mapping.py @@ -262,8 +262,15 @@ def test_backend_filtering_consistency(stage_query): f"at least one stage containing '{backend.upper()}', " \ f"but got stages: {stages}" - # Check that test does NOT map to stages of other backends - other_backends = all_backends - {backend} + # Check that test does NOT map to stages of backends it is not + # declared under (tests may legitimately be listed under several + # backends across test-db files). + declared_backends = { + b.strip() + for _, _, b in stage_query.test_map[test_name] + if b and b.strip() + } + other_backends = all_backends - declared_backends for stage in stages: stage_upper = stage.upper() for other_backend in other_backends: