fix(bundler): reject host-less catalog URLs in adapters (use hostname, not netloc) (#3333)

_validate_remote_url in bundler/services/adapters.py guarded on parsed.netloc,
which is truthy for host-less URLs like "https://:8080" or "https://user@" even
though they carry no host. so those passed the "must be a valid URL with a host"
check. its docstring says it mirrors specify_cli.catalogs validation, but that
site was already fixed to use hostname in #3210/#3227 and this twin was missed.

switch to parsed.hostname (None for host-less URLs), matching catalogs.py. this
guard runs before any network call, so it is a pre-flight safety check.

add parametrized regression tests for the host-less forms plus a valid
host+port sanity case.
This commit is contained in:
Quratulain-bilal
2026-07-07 02:44:08 +05:00
committed by GitHub
parent b5f1194168
commit c978faac57
2 changed files with 32 additions and 1 deletions

View File

@@ -69,3 +69,30 @@ def test_http_fetch_rejects_non_https_final_url(monkeypatch):
fetcher = adapters.make_catalog_fetcher(allow_network=True)
with pytest.raises(BundlerError, match="must use HTTPS"):
fetcher(_source("https://example.com/c.json"))
@pytest.mark.parametrize(
"url",
[
"https://:8080", # port only, no host
"https://:0",
"https://user@", # userinfo only, no host
"https://user:pw@",
"https://:8080/catalog.json",
],
)
def test_validate_remote_url_rejects_host_less_urls(url):
"""A URL with a truthy netloc but no host (``https://:8080``,
``https://user@``) must be rejected.
``urlparse`` gives these a non-empty ``netloc`` but ``hostname is None``,
so a ``netloc`` check would wrongly accept them. This mirrors the fix in
``specify_cli.catalogs`` (#3210), which the docstring says this validator
mirrors."""
with pytest.raises(BundlerError, match="valid URL with a host"):
adapters._validate_remote_url("team", url)
def test_validate_remote_url_accepts_normal_https_url():
# Sanity: a real host with a port still passes.
adapters._validate_remote_url("team", "https://example.com:8080/c.json")