Naming a Kestra flow 'configs' slips past the auth filter to root RCE
CISA added Kestra's CVE-2026-49869 to its known-exploited catalog on September 2 at CVSS 10.0, after an auth-filter bug let unauthenticated callers run commands as root. Teams on affected Kestra OSS builds should upgrade to 1.0.45 or 1.3.21.
The Engineer · Build desk

Six routes were left reachable without credentials. The CVSS 3.1 score is 10.0, rated Critical. The remediation deadline fell three days after the KEV listing.
| Figure | Value | Note | Claim |
|---|---|---|---|
| Routes reachable with no credentials | 6 routes | 11 | |
| CVSS 3.1 score, Critical | 10 of 10 | 2 | |
| Days, listing to deadline | 3 days | 23 |
What happened
- Kestra puts the caller's chosen flow name straight into the request URL, so a flow named 'configs' makes its routes end in /configs and the filter treats them as the public settings read.
- The suffix match left six routes reachable without credentials, including ones that create and run flows, write the key-value store, and delete flows, dashboards and audit logs.
- CISA gave federal agencies just three days to remediate, setting a September 5, 2026 deadline.
Why it matters
- exposure No credential appears anywhere in the chain, so any Kestra an attacker can reach on the network is exploitable, and firewalling the port is the real control.
- constraint Shell, Python and Node plugins are on by default, so a stock install is exploitable with no special configuration on the target.
- precedent Exploitation is already confirmed in the wild, so an unpatched instance reachable from the network should be treated as already breached.
- decision Patching forces a release-line choice, since the 1.0 branch is fixed in 1.0.45 and the 1.1-to-1.3 branch in 1.3.21.
Kestra, an open-source workflow orchestration platform, needs exactly one endpoint to answer before anyone logs in [5]. GET /api/v1/configs returns base settings a client reads first, including the auth mode and feature flags, so AuthenticationFilter makes it an exception and lets it through without credentials [6].
The exemption was written as a suffix test. Line 49 of AuthenticationFilter.java sets isConfigEndpoint = request.getPath().endsWith("/configs"), and when that check passes the filter calls chain.proceed and skips authentication [7]. The intended question is whether the request is the config endpoint. The code asks whether the path ends in /configs, and endsWith reads only the tail of a string; it has no opinion about anything in front of it [8].
The two questions diverge because Kestra builds the caller's own input into the URL. A flow route is /flows/{namespace}/{flowId}, where flowId is whatever the caller named it [9]. Name a flow configs and almost every request for that flow ends in /configs, so the filter cannot tell it apart from the settings read [10].
The same tail unlocks more than flow creation. The write-up counts six routes reachable this way [11], and flow creation plus flow execution are enough on their own [12].
The chain is three requests. A PUT to /api/v1/main/flows/tutorial/configs creates a flow whose single task is a shell command, and the server answers 200 [13]. A POST to /api/v1/main/executions/tutorial/configs runs it [14]. A GET to /api/v1/main/logs/search reads the output back [15]. None of the three sends an Authorization header [16].
The command runs as root because of two defaults. Kestra enables shell, Python and Node script plugins out of the box [17], and the worker runs inside its container as uid 0 [18]. So the planted shell task executes with root privileges, and the logs print uid=0(root) and the contents of /etc/passwd [19]. The result is root-level remote code execution inside the worker container, with no credentials anywhere in the exchange [20].
Affected builds are those below 1.0.45, and 1.1.0 up to but not including 1.3.21 [21]; the last vulnerable release on the 1.3 line is 1.3.20 [22].
What to watch
- Whether Kestra ships a configuration-level mitigation for operators who cannot upgrade right away.
- Reports of mass scanning for flow paths ending in /configs against internet-facing Kestra instances.
- Whether downstream platforms that bundle Kestra inherit the same unauthenticated route.
Clarity's read
What the record supports and how the coverage leans. The claims behind it follow.
Reality
- Evidence45
- Adoption55
- Hype gap+10
- Incentives25
- Confidence50
Claim ledger
Ranked by verification strength, evidence, and original report placement.
- [1]
On September 2, 2026, CISA added CVE-2026-49869 to its Known Exploited Vulnerabilities (KEV) catalog.
- [2]
The vulnerability's CVSS 3.1 score is 10.0, rated Critical.
- [3]
A KEV listing means exploitation of the flaw has been confirmed in the wild.
- [4]
Federal agencies were given until September 5, 2026 to remediate CVE-2026-49869.
- [5]
Kestra OSS is an open-source, event-driven workflow orchestration platform.
- [6]
GET /api/v1/configs reads base settings such as the auth mode and feature flags, and because it has to be readable before login it was made an exception in AuthenticationFilter and allowed through without credentials.
- [7]
Line 49 of AuthenticationFilter.java sets isConfigEndpoint = request.getPath().endsWith("/configs"), and when that check (or the other open-URL checks) passes the filter calls chain.proceed and skips authentication.
- [8]
endsWith looks only at the tail of a string and ignores whatever comes before it.
- [9]
Kestra's REST API embeds a caller-chosen name directly in the path, as in /flows/{namespace}/{flowId}.
- [10]
Naming a flow's flowId 'configs' makes almost every request for that flow end in /configs, which the filter cannot distinguish from the config-read endpoint.
- [11]
The single line exposed six routes: PUT create/overwrite a flow, POST run an execution, PUT write to the key-value store, DELETE a flow, DELETE a dashboard, and DELETE audit logs.
- [12]
The flow-creation and flow-execution routes alone are enough to complete a full RCE chain.
- [13]
A PUT to /api/v1/main/flows/tutorial/configs creates a flow named configs carrying a shell command, and the server returns HTTP 200.
- [14]
A POST to /api/v1/main/executions/tutorial/configs runs the flow unauthenticated and returns a RUNNING state.
- [15]
A GET to /api/v1/main/logs/search?executionId=... retrieves the command output, also unauthenticated.
- [16]
None of the three HTTP requests in the demonstrated chain carries an Authorization header.
- [17]
Kestra ships with shell, Python, Node and other script-execution plugins enabled by default.
- [18]
The worker process runs inside its container as uid=0(root) out of the box.
- [19]
The planted shell task executes with root privileges, and the logs show uid=0(root) and the contents of /etc/passwd.
- [20]
The outcome is root-level remote code execution inside the worker container, achieved with zero credentials.
- [21]
Affected versions are those below 1.0.45, and 1.1.0 up to but not including 1.3.21; the fixes are 1.0.45 and 1.3.21.
- [22]
The highest vulnerable release on the 1.3 line is 1.3.20.
- [23]
The September 5 remediation deadline fell three days after the September 2 KEV listing.
Get this ledger inside ChatGPT. Ask about any of our stories and the answer brings its figure, each claim’s verdict and the sources. Free, no account.
Sources
1 independent publisher whose own reporting we read for this story.
- dev.toIf It Ends the Same, Let It Through" — The Comparison Operator That Broke Kestra (CVE-2026-49869)
1 article · October 14, 2026
Topics and entities
Follow any of these and your For You feed starts watching them — no settings page required.