import re from pathlib import Path ROOT = Path(__file__).resolve().parents[2] WORKFLOW = ROOT / ".gitea" / "workflows" / "managed-validation.yml" def test_managed_validation_keeps_parallel_lanes_and_full_gate(): text = WORKFLOW.read_text(encoding="utf-8") for job in ("preflight:", "backend:", "frontend:", "security:", "polyglot:", "full:"): assert f" {job}" in text assert "needs: [preflight, backend, frontend, security, polyglot]" in text assert "All managed validation lanes passed." in text def test_preflight_preserves_docs_only_fast_path(): text = WORKFLOW.read_text(encoding="utf-8") assert "runtime_change" in text assert "*.md|*.mdx|docs/*" in text def test_backend_budget_is_bounded_without_weakening_validation(): text = WORKFLOW.read_text(encoding="utf-8") expected_timeouts = { "preflight": 10, "backend": 60, "frontend": 30, "security": 20, "polyglot": 30, "full": 10, } for job, expected_minutes in expected_timeouts.items(): match = re.search( rf"(?ms)^ {re.escape(job)}:\n(?P.*?)(?=^ [a-z][a-z0-9_-]*:\n|\Z)", text, ) assert match is not None, f"missing managed-validation job {job}" timeout = re.search(r"(?m)^ timeout-minutes: (\d+)\s*$", match["body"]) assert timeout is not None, f"missing timeout for {job}" assert int(timeout.group(1)) == expected_minutes for lane in ("preflight", "backend", "frontend", "security", "polyglot", "full"): assert f" {lane}:" in text assert "needs: [preflight, backend, frontend, security, polyglot]" in text assert "All managed validation lanes passed." in text backend = re.search( r"(?ms)^ backend:\n(?P.*?)(?=^ [a-z][a-z0-9_-]*:\n|\Z)", text, ) assert backend is not None backend_body = backend["body"] assert 'if [[ "${profile}" == test || "${profile}" == full ]]; then' in backend_body pytest_commands = [ line.strip() for line in backend_body.splitlines() if "-m pytest " in line ] assert pytest_commands == [ '"${py}" -m pytest backend/tests -q --durations=20' ] assert "continue-on-error" not in backend_body assert "--ignore" not in backend_body assert "--deselect" not in backend_body