PrefectHQ/fastmcp · error · ValueError

Unsupported token_endpoint_auth_method: {method!r}. Supporte

Error message

Unsupported token_endpoint_auth_method: {method!r}. Supported methods: client_secret_basic, client_secret_post, none.

What it means

The upstream OAuth client was configured with a token_endpoint_auth_method the library does not implement. Only client_secret_basic, client_secret_post, and none are supported; anything else (e.g. private_key_jwt, tls_client_auth) raises this ValueError when building the token request.

Source

Thrown at fastmcp_slim/fastmcp/server/auth/oauth_proxy/upstream.py:79

        self._client = httpx2.AsyncClient(timeout=timeout)

    async def aclose(self) -> None:
        await self._client.aclose()

    def _apply_client_auth(self, data: dict[str, Any], headers: dict[str, str]) -> None:
        """Attach client credentials per the configured auth method (RFC 6749 §2.3)."""
        method = self.token_endpoint_auth_method
        if method == "client_secret_basic":
            text = f"{self.client_id}:{self.client_secret}"
            credential = base64.b64encode(text.encode("latin1")).decode("ascii")
            headers["Authorization"] = f"Basic {credential}"
        elif method == "client_secret_post":
            data["client_id"] = self.client_id
            data["client_secret"] = self.client_secret or ""
        elif method == "none":
            data["client_id"] = self.client_id
        else:
            raise ValueError(
                f"Unsupported token_endpoint_auth_method: {method!r}. "
                "Supported methods: client_secret_basic, client_secret_post, none."
            )

    async def _request_token(self, url: str, data: dict[str, Any]) -> dict[str, Any]:
        headers = dict(_DEFAULT_TOKEN_HEADERS)
        self._apply_client_auth(data, headers)

        response = await self._client.post(url, data=data, headers=headers)
        if response.status_code >= 500:
            response.raise_for_status()

        token: dict[str, Any] = response.json()
        if "error" in token:
            raise OAuthError(
                error=token["error"], description=token.get("error_description")
            )

View on GitHub (pinned to 1f02114297)

Solutions

  1. Set token_endpoint_auth_method to one of: client_secret_basic, client_secret_post, or none
  2. If your provider requires private_key_jwt or another unsupported method, use jwt_signing_key / identity assertion support or a different auth path
  3. Check for typos and exact casing of the method string

Example fix

// before
UpstreamOAuthClient(token_endpoint_auth_method="private_key_jwt", ...)
// after
UpstreamOAuthClient(token_endpoint_auth_method="client_secret_post", ...)
Defensive patterns

Strategy: validation

Validate before calling

SUPPORTED = {"client_secret_basic", "client_secret_post", "none"}
if token_endpoint_auth_method not in SUPPORTED:
    raise ValueError(f"token_endpoint_auth_method must be one of {sorted(SUPPORTED)}")

Type guard

from typing import Literal
AuthMethod = Literal["client_secret_basic", "client_secret_post", "none"]
def is_supported_auth_method(m: str) -> TypeGuard[AuthMethod]:
    return m in {"client_secret_basic", "client_secret_post", "none"}

Try / catch

try:
    client = UpstreamOAuthClient(token_endpoint_auth_method=method, ...)
except ValueError as e:
    logger.error("bad auth method: %s", e)
    raise SystemExit(1)

Prevention

When it happens

Trigger: Constructing an upstream OAuth client with token_endpoint_auth_method set to an unsupported string (typo, or an auth method like 'private_key_jwt'), then performing any token request (fetch/refresh).

Common situations: Typo like 'client_secret_basic ' or wrong casing; copying a config from a provider that requires private_key_jwt (e.g. some enterprise IdPs); default config objects carrying methods this library hasn't implemented.

Related errors


AI-assisted analysis of PrefectHQ/fastmcp@1f02114297 (2026-08-29). Data as JSON: /api/errors/4e230c44c32c68c5. Report an issue: GitHub.