crewAIInc/crewAI · error · RuntimeError
Brave Search API connection failed: {exc}
Error message
Brave Search API connection failed: {exc} What it means
Raised when the underlying requests.get() to Brave's search endpoint throws requests.ConnectionError — DNS failure, refused connection, TLS handshake problems, or no route to host. The wrapper converts it to RuntimeError with the original exception chained. Unlike HTTP errors, connection errors are not retried by the tool's loop.
Source
Thrown at lib/crewai-tools/src/crewai_tools/tools/brave_search_tool/base.py:197
def _make_request(
self, params: dict[str, Any], *, _max_retries: int = 3
) -> dict[str, Any]:
"""Execute an HTTP GET against the Brave Search API with retry logic."""
last_resp: requests.Response | None = None
# Retry the request up to _max_retries times
for attempt in range(_max_retries):
self._rate_limit()
try:
resp = requests.get(
self.search_url,
headers=self._headers,
params=params,
timeout=self._timeout,
)
except requests.ConnectionError as exc:
raise RuntimeError(
f"Brave Search API connection failed: {exc}"
) from exc
except requests.Timeout as exc:
raise RuntimeError(
f"Brave Search API request timed out after {self._timeout}s: {exc}"
) from exc
logger.debug(
"Brave Search API request: %s %s -> %d",
"GET",
resp.url,
resp.status_code,
)
# Response was OK, return the JSON body
if resp.ok:
try:
result: dict[str, Any] = resp.json()
View on GitHub (pinned to 754d7323be)
Solutions
- Test reachability from the same environment: `curl -v https://api.search.brave.com/res/v1/web/search`.
- If a proxy is required, set HTTPS_PROXY/HTTP_PROXY env vars (requests picks them up) or add the domain to the allowlist.
- Fix container DNS/egress rules so api.search.brave.com:443 is reachable.
- Retry in your own code with backoff for transient connection drops, since the tool does not retry these.
Example fix
# before
results = tool._run("query")
# after
import os
os.environ.setdefault("HTTPS_PROXY", "http://proxy.corp:3128") # before tool use
results = tool._run("query") Defensive patterns
Strategy: retry
Validate before calling
import socket
def brave_reachable(host: str = "api.search.brave.com") -> bool:
try:
socket.create_connection((host, 443), timeout=5)
return True
except OSError:
return False Try / catch
except RuntimeError as e:
if "connection failed" in str(e):
time.sleep(3)
result = tool._run(query) # single retry; persistent failure = network/egress issue
else:
raise Prevention
- Configure HTTP(S)_PROXY env vars in proxied networks before creating/using the tool.
- Add a connectivity preflight (TCP connect to api.search.brave.com:443) to app startup.
- Open egress to api.search.brave.com:443 in container/firewall rules.
When it happens
Trigger: No internet or firewall blocking api.search.brave.com; corporate proxy requiring configuration (requests honors HTTP(S)_PROXY env vars); DNS failure in the container; TLS interception breaking the handshake.
Common situations: Corporate networks with mandatory proxies; containers with restricted egress; VPN split-tunnel dropping the API domain; transient ISP-level outages.
Related errors
- Brave Search API returned invalid JSON (HTTP {resp.status_co
- Brave Search API request timed out after {self._timeout}s: {
- Error. A valid pyproject.toml file is required. Check that a
- Invalid JSON response from {oauth_endpoint}
- Failed to connect to enterprise URL: {e!s}
AI-assisted analysis of crewAIInc/crewAI@754d7323be (2026-08-15).
Data as JSON: /api/errors/35660e6c3c828fe8.
Report an issue: GitHub.