encode/httpx · error · NotImplementedError

Digest auth-int support is not yet implemented

Error message

Digest auth-int support is not yet implemented

What it means

Raised as NotImplementedError by DigestAuth._resolve_qop when the server's qop list contains only 'auth-int'. httpx implements qop=auth but not qop=auth-int (which requires hashing the request body for integrity), so a server that offers exclusively integrity protection cannot be negotiated.

Source

Thrown at httpx/_auth.py:337

                header_value += ", "
            template = (
                QUOTED_TEMPLATE
                if field not in NON_QUOTED_FIELDS
                else NON_QUOTED_TEMPLATE
            )
            header_value += template.format(field, to_str(value))

        return header_value

    def _resolve_qop(self, qop: bytes | None, request: Request) -> bytes | None:
        if qop is None:
            return None
        qops = re.split(b", ?", qop)
        if b"auth" in qops:
            return b"auth"

        if qops == [b"auth-int"]:
            raise NotImplementedError("Digest auth-int support is not yet implemented")

        message = f'Unexpected qop value "{qop!r}" in digest auth'
        raise ProtocolError(message, request=request)


class _DigestAuthChallenge(typing.NamedTuple):
    realm: bytes
    nonce: bytes
    algorithm: str
    opaque: bytes | None
    qop: bytes | None

View on GitHub (pinned to b5addb64f0)

Solutions

  1. Reconfigure the server to also offer qop=auth alongside auth-int.
  2. Switch away from httpx.DigestAuth to a bearer-token or BasicAuth scheme if the endpoint allows it.
  3. Fall back to a different HTTP library that implements auth-int, or vendor a patched _resolve_qop.

Example fix

// before
client.get(url, auth=httpx.DigestAuth("u", "p"))
// after
# server config: change qop="auth-int" to qop="auth,auth-int"
client.get(url, auth=httpx.DigestAuth("u", "p"))
Defensive patterns

Strategy: try-catch

Validate before calling

import re
probe = client.get(url)
wa = probe.headers.get_list("www-authenticate") if probe.status_code == 401 else []
for h in wa:
    if h.lower().startswith("digest "):
        m = re.search(r'qop="?([^"]+)"?', h)
        if m:
            qops = [q.strip() for q in m.group(1).split(",")]
            only_auth_int = "auth" not in qops and qops == ["auth-int"]
            # if only_auth_int, DigestAuth will raise NotImplementedError

Type guard

def digest_supports_auth(www_auth_values: list[str]) -> bool:
    import re
    for h in www_auth_values:
        if h.lower().startswith("digest "):
            m = re.search(r'qop="?([^"]+)"?', h)
            if m and "auth" in [q.strip() for q in m.group(1).split(",")]:
                return True
    return False

Try / catch

try:
    resp = client.get(url, auth=httpx.DigestAuth(user, pw))
except NotImplementedError:
    # Server requires auth-int which httpx does not implement
    resp = client.get(url, headers={"Authorization": "Bearer <token>"})

Prevention

When it happens

Trigger: Using httpx.DigestAuth against a server whose 401 challenge declares qop="auth-int" with no "auth" alternative (e.g. 'Digest ... qop="auth-int"'). _resolve_qop splits qop and only proceeds if 'auth' is present.

Common situations: Strict enterprise gateways or SIP-style services that mandate body integrity protection; security-hardened servers that disable qop=auth.

Related errors


AI-assisted analysis of encode/httpx@b5addb64f0 (2026-08-04). Data as JSON: /data/errors/41e5f47b1f3e4b13.json. Report an issue: GitHub.