{"record":{"id":"1efa294b36d1cb01","repo":"bytedance/deer-flow","slug":"not-authenticated-1efa29","errorCode":null,"errorMessage":"Not authenticated","messagePattern":"Not authenticated","errorType":"http","errorClass":"HTTPException","httpStatus":401,"severity":"error","filePath":"backend/app/gateway/langgraph_auth.py","lineNumber":78,"sourceCode":"\n@auth.authenticate\nasync def authenticate(request):\n    \"\"\"Validate the session cookie, decode JWT, and check token_version.\n\n    Same validation chain as Gateway's get_current_user_from_request:\n      cookie → decode JWT → DB lookup → token_version match\n    Also enforces CSRF on state-changing methods.\n    \"\"\"\n    # CSRF check before authentication so forged cross-site requests\n    # are rejected early, even if the cookie carries a valid JWT.\n    _check_csrf(request)\n\n    if is_auth_disabled():\n        return AUTH_DISABLED_USER_ID\n\n    token = request.cookies.get(\"access_token\")\n    if not token:\n        raise Auth.exceptions.HTTPException(\n            status_code=401,\n            detail=\"Not authenticated\",\n        )\n\n    payload = decode_token(token)\n    if isinstance(payload, TokenError):\n        raise Auth.exceptions.HTTPException(\n            status_code=401,\n            detail=\"Invalid token\",\n        )\n\n    user = await get_local_provider().get_user(payload.sub)\n    if user is None:\n        raise Auth.exceptions.HTTPException(\n            status_code=401,\n            detail=\"User not found\",\n        )\n    if user.token_version != payload.ver:","sourceCodeStart":60,"sourceCodeEnd":96,"githubUrl":"https://github.com/bytedance/deer-flow/blob/1dd6ba1acb03700589994b0366c5d1c7d05e2eff/backend/app/gateway/langgraph_auth.py#L60-L96","documentation":"Raised by the LangGraph-compatible auth dependency when the request carries no `access_token` cookie. The handler runs a CSRF check first, then short-circuits with HTTP 401 the moment the cookie is absent, before any JWT decode or DB lookup. It means the caller never presented credentials at all, not that they presented bad ones.","triggerScenarios":"Calling any `/api/langgraph/*` route (thread create, runs, streams) without first logging in via the auth flow that sets the `access_token` cookie; using a fetch/axios client configured with `credentials: 'omit'` or `same-origin` from a cross-origin origin; a browser session where the cookie expired and was dropped; hitting the API with a raw Bearer-token-style client when this stack only reads cookies.","commonSituations":"Scripts or integrations that assume Authorization headers work; cross-origin frontend misconfiguring credentials; cookie expiry (no refresh attempted); auth disabled flag not set in local dev so a previously-open endpoint now demands a cookie.","solutions":["Log in through the login endpoint to obtain the `access_token` cookie and reuse the cookie jar in subsequent requests","For cross-origin frontends, send requests with `credentials: 'include'` and ensure the server CORS config allows credentials","If this is an unauthenticated local/dev deployment, set the auth-disabled config so the dependency returns AUTH_DISABLED_USER_ID","If automating, drive the login flow once and persist cookies (e.g. requests.Session) instead of hand-crafting headers"],"exampleFix":"// before\nconst res = await fetch('https://host/api/langgraph/threads', {\n  headers: { Authorization: 'Bearer ...' }, // cookie never sent\n});\n// after\nconst res = await fetch('https://host/api/langgraph/threads', {\n  credentials: 'include', // sends access_token cookie\n});","handlingStrategy":"validation","validationCode":"import requests\n\ns = requests.Session()\nresp = s.post(f\"{base}/api/auth/login\", json={\"username\": u, \"password\": p})\nassert resp.ok, \"login failed\"\nassert \"access_token\" in s.cookies, \"no access_token cookie set — later calls will 401\"","typeGuard":null,"tryCatchPattern":"try {\n  await api.getThreads();\n} catch (e) {\n  if (e.status === 401 && e.detail === 'Not authenticated') {\n    await login(); // then retry once\n  } else throw e;\n}","preventionTips":["Centralize API calls in one client that always sends credentials: 'include'","After any login flow, assert the access_token cookie exists before proceeding","Treat detail 'Not authenticated' as a signal to run the login flow, not to retry the same request"],"tags":["auth","http-401","cookies","langgraph"],"backgroundTag":null,"analyzedSha":"1dd6ba1acb03700589994b0366c5d1c7d05e2eff","analyzedAt":"2026-08-14T21:20:34.804Z","schemaVersion":2},"datasetVersion":"2026-08-15T17:31:12.345Z"}