system: OPERATIONAL
← back to all hacks
INFRASTRUCTURE CRITICAL NEW

Cross-tenant flow hijacking in Langflow via a broken authorization check

A CISA-listed authorization flaw in Langflow's OpenAI-compatible responses endpoint lets any authenticated user run another tenant's flow — and harvest the API keys embedded in it.

2026-07-19 // 6 min affects: langflow

What is this?

Langflow is a widely deployed open-source visual framework for building LLM agents and retrieval-augmented pipelines. On June 19, 2026, its maintainers published a security advisory for an insecure direct object reference (IDOR) in the /api/v1/responses endpoint: any authenticated user could execute a flow belonging to another user simply by passing that flow’s identifier in the request. The endpoint accepted a client-supplied flow ID but never checked that the caller owned it.

The flaw matters because Langflow flows routinely embed live secrets — LLM provider keys, cloud credentials, database strings — directly in their component configuration. Hijacking someone else’s flow therefore isn’t just unauthorized execution; it is a path to their credentials. Sysdig’s Threat Research Team reported the first known in-the-wild exploitation on June 25, 2026, and the US CISA added the vulnerability to its Known Exploited Vulnerabilities catalog on July 7, 2026, with a July 10 remediation deadline for federal civilian agencies. The fix shipped earlier, in Langflow 1.9.1.

How it works

The root cause is a single missing ownership check in the get_flow_by_id_or_endpoint_name helper (helpers/flow.py). When a flow is looked up by human-readable endpoint_name, the query is scoped to the current user. When the same flow is looked up by UUID, it is not:

# Illustrative — the vulnerable branch resolved a flow by UUID
# without confirming the requester owned it.
flow_id = UUID(flow_id_or_name)
flow = await session.get(Flow, flow_id)   # no owner check on this path
# ...
# The endpoint_name branch, by contrast, DID filter on user_id.

The /api/v1/responses endpoint is OpenAI-Responses-compatible: it treats the model field as a flow UUID. Feed it another tenant’s UUID and the platform runs that tenant’s flow — under that tenant’s embedded credentials — through its own blessed execution path.

There is one honest constraint, and it is worth stating plainly: a Langflow flow UUID is a random 122-bit value. It cannot be brute-forced, and the endpoint_name path is properly scoped, so there is no slug-guessing shortcut. Exploitation depends on first obtaining a valid flow ID. In the observed intrusion, the operator pulled the GET /api/v1/flows/ listing — which over-shared IDs — then replayed those IDs against the responses endpoint. This is the textbook disclosure-to-IDOR chain: an over-permissive listing endpoint is what turns an “unguessable” object reference into a working attack.

Example prompt

The snippet below shows the technique defensively: the responses endpoint treated the model field as a flow UUID and executed it without an ownership check, so a leaked flow ID could run another tenant’s flow under their embedded keys. No working exploit is shown — this is for defenders.

# Langflow cross-tenant flow hijack (illustrative, defensive)
# The /api/v1/responses endpoint treats "model" as a flow UUID and
# ran it WITHOUT checking the caller owned it (pre-1.9.1):
victim_flow_id = "[REDACTED-flow-uuid]"   # first leaked via GET /api/v1/flows/
POST /api/v1/responses  { "model": victim_flow_id, "input": "[hidden instruction]" }
# -> runs another tenant's flow under THEIR embedded API keys.
# Root cause: missing ownership check on the UUID lookup path (IDOR).
# Defense: upgrade to Langflow 1.9.1+, scope object lookups to the caller,
# authorize/rate-limit ID-listing endpoints, and vault your secrets.

Why it matters

The instructive part of this case is that CVSS score is not an exploitation ranking. The flow-authorization flaw scores a 9.9 because it breaks cross-tenant scope, yet Sysdig watched the same operator treat it as a two-request afterthought while pouring sustained effort into a separate, unauthenticated remote-code-execution flaw in the same product (scored lower, at 9.3, but internet-sprayable and requiring no credentials). On a single self-hosted box, code execution is a strict superset of what the IDOR buys you, so attackers optimizing for effort-to-yield reach for the RCE.

The IDOR earns its severity in exactly one setting: multi-tenant or managed Langflow. There, tenant flows run in isolated workers, so the RCE is contained per tenant and cannot, by itself, cross the boundary. The authorization flaw can — quietly, at the application layer, as a legitimate-looking API call whose only anomaly is the wrong flow ID. For anyone operating Langflow as a shared service, this is the path that reaches another customer’s secrets, and it sits well below the detection footprint of the noisy RCE.

The broader lesson generalizes past this one product. AI orchestration platforms concentrate credentials by design, which makes them high-value targets, and their fast-moving codebases keep shipping classic web-authorization bugs. Treat these platforms with the same access-control scrutiny you would apply to any multi-tenant SaaS.

Defenses

  1. Patch and confirm the version. The fix landed in Langflow 1.9.1 (PR #12832); run the latest release. Ownership is now enforced on both lookup branches, and cross-user lookups return a 404 rather than a 403 to avoid an existence oracle.
  2. Treat ID-disclosure endpoints as part of the IDOR’s attack surface. The listing route that leaked flow UUIDs is what made the flaw reachable. Object-enumeration endpoints deserve the same authorization review and rate-limiting as the sensitive actions they unlock.
  3. Stop embedding raw secrets in flows. Reference credentials through a secrets manager or platform variable store rather than pasting provider and cloud keys into component configs. If a flow was exposed, rotate every key it carried — assume harvest.
  4. Do not expose self-hosted instances unauthenticated. The observed operator probed the no-auth auto_login default first. Put Langflow behind authentication and network controls; never publish an admin-capable instance to the open internet.
  5. Enforce isolation at the application layer for multi-tenant deployments. Per-tenant worker sandboxing does not stop an app-layer authorization break. Scope every object lookup to the caller and test the cross-tenant case explicitly.
  6. Monitor for the chain, not just the payload. An enumeration call (/api/v1/flows/) immediately followed by /api/v1/responses calls carrying freshly listed IDs is a strong signal. Sysdig and SentinelOne have published indicators of compromise for the observed campaign.

Status

ItemReferenceDateNotes
Vendor advisory (IDOR, CWE-639)GHSA-qrpv-q767-xqq2 / CVE-2026-552552026-06-19CVSS 9.9, scope-changed; affects < 1.9.1
Fix releasedLangflow 1.9.1 (PR #12832)2026-04-22 (merged)Ownership enforced on both lookup paths
First in-the-wild exploitationSysdig TRT2026-06-25Enumeration → responses chain; “leak api keys” prompt
Added to CISA KEVCISA alert2026-07-07Federal remediation deadline 2026-07-10
Chained RCE (same product)CVE-2026-33017KEV 2026-03-25Unauthenticated, CVSS 9.3, mass-exploited within ~20h

Responsible disclosure was observed: the reporters were credited and a patch was released before the public advisory. The right takeaway is not “another AI CVE” but a reminder that classic broken-authorization bugs are now landing in the tools that hold your model and cloud keys — and that a high CVSS number tells you about impact, not about which flaw an attacker will actually reach first.

Sources