langflow-ai/langflow · error · HTTPException
Not Found
Error message
Not Found
What it means
Raised by _require_a2a_enabled on every A2A router route (/.well-known agent card and /{flow_id}/jsonrpc) when the settings flag a2a_enabled is falsy. It reads live settings per request, so the 404 appears until the flag is set (env LANGFLOW_A2A_ENABLED or config) — regardless of whether the flow itself is A2A-capable. A 404 (not 403) is used so a disabled feature is indistinguishable from a non-existent route.
Source
Thrown at src/backend/base/langflow/api/v1/a2a.py:96
)
from langflow.helpers.flow import get_flow_by_id_or_endpoint_name
from langflow.helpers.user import get_user_by_flow_id_or_endpoint_name
from langflow.services.database.models import A2ACheckpoint, A2ATask, Flow
from langflow.services.database.models.api_key.crud import check_key
from langflow.services.database.models.flow.model import FlowType
router = APIRouter(prefix="/a2a", tags=["a2a"])
def _require_a2a_enabled() -> None:
"""Return 404 when the A2A feature flag is off.
Reads the live settings per request (after env/dotenv load), matching
langflow.api.v1.extensions._require_extension_reload_enabled.
"""
settings = get_settings_service().settings
if not getattr(settings, "a2a_enabled", False):
raise HTTPException(status_code=status.HTTP_404_NOT_FOUND, detail="Not Found")
async def _enforce_a2a_auth(flow: Flow, request: Request) -> None:
"""Enforce the folder's auth scheme before any dispatch, failing closed on the rest.
The flow always runs as its owner (see ``_run_flow``), so an unauthenticated run is a
run under the owner's identity. Gate by the folder's ``auth_type``:
- ``"none"`` / missing / no-folder -> public agent (the intended public A2A model).
- ``"apikey"`` / ``"oauth"`` -> require a valid langflow API key in ``x-api-key`` whose
owner is the flow owner. An oauth folder is fronted by an external OAuth broker (the dance
happens in front); the langflow transport itself still takes an owner-scoped api key,
exactly as the MCP transport does (``mcp_projects.verify_project_auth``), since credential
forwarding from the broker isn't available yet. Accepting another user's valid key would
let them trigger a run under the owner's identity, so scope to ``flow.user_id``.
- anything else (an auth type A2A doesn't understand) -> fail closed with 403: treating a
*protected* folder as public would expose an owner-identity run anonymously.
View on GitHub (pinned to 976ec789d2)
Solutions
- Set LANGFLOW_A2A_ENABLED=true in the server environment (or .env) and restart
- Verify the variable name/spelling and that the process actually sees it: print get_settings_service().settings.a2a_enabled in a shell or check the /settings endpoint
- Ensure ALL workers/replicas have the flag, not just one container
Example fix
# before docker compose up # LANGFLOW_A2A_ENABLED unset # after LANGFLOW_A2A_ENABLED=true docker compose up
Defensive patterns
Strategy: validation
Validate before calling
import httpx
def a2a_enabled(base_url: str) -> bool:
# cheapest probe: agent card for a known-agent flow returns 404 'Not Found' both when
# the flag is off and for unknown flows; a 200 on any agent flow proves the flag is on.
r = httpx.get(f"{base_url}/api/v1/a2a/{AGENT_FLOW_ID}/card")
return r.status_code != 404 or "a2a_enabled" in r.text # refine per deployment Try / catch
try:
card = client.get_agent_card()
except Exception as e:
if "404" in str(e) or "Not Found" in str(e):
raise ConfigError("LANGFLOW_A2A_ENABLED is off or flow not an a2a agent") from e
raise Prevention
- Health-check A2A availability at deploy time before wiring clients
- Set LANGFLOW_A2A_ENABLED in infrastructure-as-code so every worker gets it
- Treat 404 on A2A routes as 'feature off or wrong flow' — check settings first
When it happens
Trigger: GET /api/v1/a2a/... or POST /api/v1/a2a/{flow_id}/jsonrpc on a server started without LANGFLOW_A2A_ENABLED=true (or before .env load set it). Also mid-session after the flag was turned off, since settings are read per request.
Common situations: Deploying an A2A client against a default OSS install where the feature ships off; setting the env var only in one of several workers / docker-compose services; forgetting that the flag is read after dotenv load so a typo in the variable name silently keeps it disabled.
Related errors
- This endpoint is not available
- Failed to load file (HTTP ${status})
- reload-in-progress
- Failed to download files: ${response.statusText}
- Failed to delete MCP Server
AI-assisted analysis of langflow-ai/langflow@976ec789d2 (2026-08-14).
Data as JSON: /api/errors/37782d3c201b14a6.
Report an issue: GitHub.