unclecode/crawl4ai · error · ConnectionError
Authentication failed: {str(e)}
Error message
Authentication failed: {str(e)} What it means
Raised by Crawl4aiDockerClient authentication when the POST {base_url}/token request fails at the transport level or returns a non-2xx status (httpx.RequestError or httpx.HTTPStatusError). The underlying cause is wrapped into a ConnectionError with the original httpx message, so the detail string is the authoritative clue.
Source
Thrown at crawl4ai/docker_client.py:63
headers={"Content-Type": "application/json"}
)
self._token: Optional[str] = None
async def authenticate(self, email: str) -> None:
"""Authenticate with the server and store the token."""
url = urljoin(self.base_url, "/token")
try:
self.logger.info(f"Authenticating with email: {email}", tag="AUTH")
response = await self._http_client.post(url, json={"email": email})
response.raise_for_status()
data = response.json()
self._token = data["access_token"]
self._http_client.headers["Authorization"] = f"Bearer {self._token}"
self.logger.success("Authentication successful", tag="AUTH")
except (httpx.RequestError, httpx.HTTPStatusError) as e:
error_msg = f"Authentication failed: {str(e)}"
self.logger.error(error_msg, tag="ERROR")
raise ConnectionError(error_msg)
async def _check_server(self) -> None:
"""Check if server is reachable, raising an error if not."""
try:
await self._http_client.get(urljoin(self.base_url, "/health"))
self.logger.success(f"Connected to {self.base_url}", tag="READY")
except httpx.RequestError as e:
self.logger.error(f"Server unreachable: {str(e)}", tag="ERROR")
raise ConnectionError(f"Cannot connect to server: {str(e)}")
def _prepare_request(
self,
urls: List[str],
browser_config: Optional[BrowserConfig] = None,
crawler_config: Optional[CrawlerRunConfig] = None,
hooks: Optional[Union[Dict[str, Callable], Dict[str, str]]] = None,
hooks_timeout: int = 30
) -> Dict[str, Any]:View on GitHub (pinned to 7e80152142)
Solutions
- Verify the server is up first: curl {base_url}/health should return 200
- Check base_url spelling, scheme, and port against the container's published port
- Read str(e) inside the message — 'ConnectError' means unreachable host, '401/404/422' means the endpoint exists but rejected the request
- If the server logs show token-endpoint errors, restart or reconfigure the crawl4ai Docker server image
Example fix
// before
client = Crawl4aiDockerClient(base_url="http://localhost:11235")
await client.authenticate("user@example.com") # ConnectionError
// after
# confirm health first, then authenticate
import httpx
resp = await httpx.AsyncClient().get("http://localhost:11235/health")
assert resp.status_code == 200, "start the crawl4ai server container first"
await client.authenticate("user@example.com") Defensive patterns
Strategy: try-catch
Validate before calling
import httpx
async def server_ready(base_url: str) -> bool:
try:
r = await httpx.AsyncClient().get(f"{base_url}/health", timeout=5)
return r.status_code == 200
except httpx.HTTPError:
return False
if not await server_ready(client.base_url):
raise RuntimeError("crawl4ai server not reachable") Try / catch
try:
await client.authenticate(email)
except ConnectionError as e:
# str(e) contains the httpx detail: host vs status cause
log.error("auth failed: %s", e)
raise Prevention
- Health-check {base_url}/health before authenticating
- Pin the docker server image version to match the client
- Surface the embedded httpx detail — it distinguishes unreachable host from rejected request
When it happens
Trigger: Calling the client's authenticate/email-token flow when the Docker/server instance is unreachable, base_url points to the wrong host or port, TLS is misconfigured, or the /token endpoint rejects the request (e.g. 4xx because the email payload is refused).
Common situations: The crawl4ai server container is not running or is still starting up; base_url uses http:// against an https endpoint or a wrong port; DNS/firewall blocks the host; a reverse proxy in front of the server strips or rejects the /token route.
Understand the failure class
- Authentication and authorization failures — expired tokens, bad credentials, and missing scopes.
Related errors
- Cannot connect to server: {str(e)}
- Request timed out: {str(e)}
- Failed to connect: {str(e)}
- [NSTProxy] API Error: {data.get('msg', 'Unknown error')}
- Failed on navigating ACS-GOTO: {str(e)}
AI-assisted analysis of unclecode/crawl4ai@7e80152142 (2026-08-14).
Data as JSON: /api/errors/0feddab749e7f5dc.
Report an issue: GitHub.