{"id":"ca47ea2b3fbbf04a","repo":"encode/httpx","slug":"relative-urls-cannot-have-a-path-starting-with","errorCode":null,"errorMessage":"Relative URLs cannot have a path starting with '//'","messagePattern":"Relative URLs cannot have a path starting with '//'","errorType":"validation","errorClass":"InvalidURL","httpStatus":null,"severity":"error","filePath":"httpx/_urlparse.py","lineNumber":439,"sourceCode":"\ndef validate_path(path: str, has_scheme: bool, has_authority: bool) -> None:\n    \"\"\"\n    Path validation rules that depend on if the URL contains\n    a scheme or authority component.\n\n    See https://datatracker.ietf.org/doc/html/rfc3986.html#section-3.3\n    \"\"\"\n    if has_authority:\n        # If a URI contains an authority component, then the path component\n        # must either be empty or begin with a slash (\"/\") character.\"\n        if path and not path.startswith(\"/\"):\n            raise InvalidURL(\"For absolute URLs, path must be empty or begin with '/'\")\n\n    if not has_scheme and not has_authority:\n        # If a URI does not contain an authority component, then the path cannot begin\n        # with two slash characters (\"//\").\n        if path.startswith(\"//\"):\n            raise InvalidURL(\"Relative URLs cannot have a path starting with '//'\")\n\n        # In addition, a URI reference (Section 4.1) may be a relative-path reference,\n        # in which case the first path segment cannot contain a colon (\":\") character.\n        if path.startswith(\":\"):\n            raise InvalidURL(\"Relative URLs cannot have a path starting with ':'\")\n\n\ndef normalize_path(path: str) -> str:\n    \"\"\"\n    Drop \".\" and \"..\" segments from a URL path.\n\n    For example:\n\n        normalize_path(\"/path/./to/somewhere/..\") == \"/path/to\"\n    \"\"\"\n    # Fast return when no '.' characters in the path.\n    if \".\" not in path:\n        return path","sourceCodeStart":421,"sourceCodeEnd":457,"githubUrl":"https://github.com/encode/httpx/blob/b5addb64f0161ff6bfe94c124ef76f6a1fba5254/httpx/_urlparse.py#L421-L457","documentation":"Raised by validate_path when a relative URL (no scheme and no authority) has a path beginning with '//'. Per RFC 3986 §4.2, '//path' would be parsed as an authority, leaving an empty host; rather than silently mis-parsing, httpx rejects it. A leading '//' on a scheme-less URL is almost always a typo or a missing scheme.","triggerScenarios":"httpx.URL('//example.com/path') (no scheme), or httpx.URL(path='//foo').","commonSituations":"Dropping the 'https:' from a copied URL but keeping '//'; building protocol-relative URLs as httpx.URL objects (they are only valid in HTML context, not as a request target); missing scheme when concatenating.","solutions":["Provide a scheme: httpx.URL('https://example.com/path').","If the URL is intentionally relative, prefix the path with a single '/' or remove the leading slashes.","Detect protocol-relative strings at input time and prepend a default scheme.","Use urljoin with a base URL to resolve relative references."],"exampleFix":"// before\nurl = httpx.URL(\"//example.com/path\")  # InvalidURL\n\n// after\nurl = httpx.URL(\"https://example.com/path\")","handlingStrategy":"validation","validationCode":"def absolutize(url: str, default_scheme: str = \"https\") -> str:\n    if url.startswith(\"//\"):\n        return f\"{default_scheme}:{url}\"\n    return url\n\nurl = httpx.URL(absolutize(user_url))","typeGuard":"def is_protocol_relative(url: str) -> bool:\n    return url.startswith(\"//\") and not url.startswith(\"///\")","tryCatchPattern":"from httpx import InvalidURL\n\ntry:\n    url = httpx.URL(maybe_relative)\nexcept InvalidURL as e:\n    if \"cannot have a path starting with '//'\" in str(e):\n        url = httpx.URL(\"https:\" + maybe_relative)\n    else:\n        raise","preventionTips":["Reject or repair protocol-relative URLs at the input boundary.","Always supply a scheme when constructing httpx.URL objects for requests.","Use urljoin with a real base URL to resolve relative references."],"tags":["url","path","rfc3986","relative-url","validation"],"analyzedSha":"b5addb64f0161ff6bfe94c124ef76f6a1fba5254","analyzedAt":"2026-08-04T19:32:56.768Z","schemaVersion":2}