From d99a7126900ae82895c6fc2fb99a192b7b0ae8e0 Mon Sep 17 00:00:00 2001 From: Emma Smith Date: Wed, 21 May 2025 09:14:36 -0400 Subject: [PATCH 1/2] gh-134262: Add retries to generate_sbom.py (GH-134263) (cherry picked from commit 0c5a8b0b55238a45b9073d06a10c3a59568cdf3c) Co-authored-by: Emma Smith Co-authored-by: Semyon Moroz --- Tools/build/generate_sbom.py | 19 ++++++++++++++++++- 1 file changed, 18 insertions(+), 1 deletion(-) diff --git a/Tools/build/generate_sbom.py b/Tools/build/generate_sbom.py index db01426e9722c3..5845f2d85c7fdb 100644 --- a/Tools/build/generate_sbom.py +++ b/Tools/build/generate_sbom.py @@ -7,7 +7,9 @@ import re import subprocess import sys +import time import typing +import urllib.error import urllib.request from pathlib import Path, PurePosixPath, PureWindowsPath @@ -161,6 +163,21 @@ def get_externals() -> list[str]: return externals +def download_with_retries(download_location: str, + max_retries: int = 5, + base_delay: float = 2.0) -> typing.Any: + """Download a file with exponential backoff retry.""" + for attempt in range(max_retries): + try: + resp = urllib.request.urlopen(download_location) + except urllib.error.URLError as ex: + if attempt == max_retries: + raise ex + time.sleep(base_delay**attempt) + else: + return resp + + def check_sbom_packages(sbom_data: dict[str, typing.Any]) -> None: """Make a bunch of assertions about the SBOM package data to ensure it's consistent.""" @@ -175,7 +192,7 @@ def check_sbom_packages(sbom_data: dict[str, typing.Any]) -> None: # and that the download URL is valid. if "checksums" not in package or "CI" in os.environ: download_location = package["downloadLocation"] - resp = urllib.request.urlopen(download_location) + resp = download_with_retries(download_location) error_if(resp.status != 200, f"Couldn't access URL: {download_location}'") package["checksums"] = [{ From d2f37afd871f0615552ce2cc4636356362957092 Mon Sep 17 00:00:00 2001 From: Zachary Ware Date: Wed, 28 May 2025 18:27:44 -0500 Subject: [PATCH 2/2] Fix off-by-one (cherry-picked from commit e64395e8eb8d3a9e35e3e534e87d427ff27ab0a5) --- Tools/build/generate_sbom.py | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/Tools/build/generate_sbom.py b/Tools/build/generate_sbom.py index 5845f2d85c7fdb..89f8f83999c47e 100644 --- a/Tools/build/generate_sbom.py +++ b/Tools/build/generate_sbom.py @@ -167,7 +167,7 @@ def download_with_retries(download_location: str, max_retries: int = 5, base_delay: float = 2.0) -> typing.Any: """Download a file with exponential backoff retry.""" - for attempt in range(max_retries): + for attempt in range(max_retries + 1): try: resp = urllib.request.urlopen(download_location) except urllib.error.URLError as ex: