dotnet/aspnetcore · error · Exception
Failed to download {url}, Status Code: {response.status}
Error message
Failed to download {url}, Status Code: {response.status} What it means
download_file raises a plain Exception when the HTTP response status is not 200, including the status code in the message. This fires before any retry accounting for the body — non-200 statuses are treated as download failures. The exception is caught by the except clause below (CancelledError/TimeoutError/ClientError) only for those specific types; a status-code Exception is re-raised and terminates the loop because it is not in the caught tuple, so it propagates immediately rather than retrying.
Source
Thrown at eng/common/cross/install-debs.py:40
attempt = 0
while attempt < max_retries:
try:
async with session.get(url, timeout=aiohttp.ClientTimeout(total=timeout)) as response:
if response.status == 200:
with open(dest_path, "wb") as f:
content = await response.read()
# verify checksum if provided
if checksum:
sha256 = hashlib.sha256(content).hexdigest()
if sha256 != checksum:
raise Exception(f"SHA256 mismatch for {url}: expected {checksum}, got {sha256}")
f.write(content)
print(f"Downloaded {url} at {dest_path}")
return
else:
raise Exception(f"Failed to download {url}, Status Code: {response.status}")
except (asyncio.CancelledError, asyncio.TimeoutError, aiohttp.ClientError) as e:
print(f"Error downloading {url}: {type(e).__name__} - {e}. Retrying...")
attempt += 1
await asyncio.sleep(retry_delay)
raise Exception(f"Failed to download {url} after {max_retries} attempts.")
async def download_deb_files_parallel(mirror, packages, tmp_dir):
"""Download .deb files in parallel."""
os.makedirs(tmp_dir, exist_ok=True)
tasks = []
timeout = aiohttp.ClientTimeout(total=60)
async with aiohttp.ClientSession(timeout=timeout) as session:
for pkg, info in packages.items():
filename = info.get("Filename")
if filename:View on GitHub (pinned to 294cab2f9b)
Solutions
- Confirm the --suite and --arch combination exists on the --mirror (open the dists/<suite>/ URL in a browser).
- For 404 on a specific package, the suite may have moved the package — try a different suite or pin to a snapshot mirror.
- For 403/429, reduce parallelism or use a different mirror that does not rate-limit.
- Note: status-code errors do not retry by design; fix the URL/mirror rather than expecting the retry loop to help.
- Temporarily remove --force-check-gpg to isolate whether the failure is the Release/Packages fetch vs the .deb fetch.
Example fix
# before — wrong suite for the package python3 install-debs.py --suite stretch --mirror http://deb.debian.org/debian ... # 404 on libc6 # after python3 install-debs.py --suite bookworm --mirror http://deb.debian.org/debian ...
Defensive patterns
Strategy: try-catch
Validate before calling
# HEAD the URL before the bulk download to fail fast on 404/403
import aiohttp
async with aiohttp.ClientSession() as s:
async with s.head(url) as h:
if h.status != 200:
print(f'Pre-flight {h.status} for {url}; aborting before retry loop')
return False Try / catch
try:
await download_file(session, url, dest, checksum=checksum)
except Exception as e:
msg = str(e)
if 'Status Code:' in msg:
code = int(msg.split('Status Code:')[1].strip())
if code in (404, 410):
print(f'Package permanently gone: {url}')
raise # not retryable
# other codes might warrant a mirror switch
raise Prevention
- Validate --suite/--arch exist on the mirror before the bulk download.
- Note that status-code errors bypass the retry loop by design; fix the URL.
- Use HEAD requests to pre-flight package availability.
- Log the failing URL and status to distinguish transient from permanent failures.
When it happens
Trigger: A .deb URL or Release/Packages URL returns 404 (package removed from the suite), 403 (mirror access denied), or 5xx (mirror error). The Exception raised inside the try is NOT in the (CancelledError, TimeoutError, ClientError) tuple, so it escapes the retry loop and surfaces directly.
Common situations: Package was removed from the suite but the Packages index still references it; mirror requires authentication or blocks user-agents; CDN rate-limiting returns 429; wrong --suite producing 404s for the requested components.
Related errors
- SHA256 mismatch for {url}: expected {checksum}, got {sha256}
- Failed to download {url} after {max_retries} attempts.
- SHA256 mismatch for {path}: expected {packages_sha}, got {sh
- Signature verification failed: {result.stderr.decode('utf-8'
- Could not find checksum for {path} in Release file.
AI-assisted analysis of dotnet/aspnetcore@294cab2f9b (2026-08-06).
Data as JSON: /api/errors/1b4aa6077aa208c5.
Report an issue: GitHub.