CVE-2026-69146
Summary
When MLflow is deployed with the built-in basic-auth plugin (--app-name basic-auth), any authenticated user can inject arbitrary dataset records into another user's run by calling POST /api/2.0/mlflow/runs/log-inputs. The LogInputs proto handler is absent from the BEFORE_REQUEST_HANDLERS map in mlflow/server/auth/init.py, so the before-request hook skips authorization entirely and the request succeeds. Standard write endpoints on the same run -- such as POST /api/2.0/mlflow/runs/log-metric -- correctly return HTTP 403.
Details
MLflow's basic-auth app gates every HTTP handler through a before-request hook (_before_request) that looks up the relevant permission validator in BEFORE_REQUEST_VALIDATORS. Validators are built from the BEFORE_REQUEST_HANDLERS dictionary, which maps each protobuf request class to a callable. When a class is absent from the dict (or mapped to None), get_before_request_handler returns None, and the resulting entry in BEFORE_REQUEST_VALIDATORS is (path, method): None.
Inside _before_request:
mlflow/server/auth/init.py _before_request()
if validator := _find_validator(request): # None is falsy -- branch skipped
if not validator():
return make_forbidden_response()
elif _is_proxy_artifact_path(request.path): # not a proxy path
...
falls through: any authenticated request is allowed
The LogInputs protobuf class is not present in BEFORE_REQUEST_HANDLERS:
mlflow/server/auth/init.py BEFORE_REQUEST_HANDLERS dict
LogInputs is absent; all run-write operations below ARE present:
LogBatch: validate_can_update_run,
LogMetric: validate_can_update_run,
SetTag: validate_can_update_run,
LogParam: validate_can_update_run,
LogInputs: <missing>
The route /api/2.0/mlflow/runs/log-inputs (and the identical /ajax-api/ variant) therefore admits any valid credential, regardless of which experiment or run is targeted. The LogInputs handler writes DatasetInput records directly to the run's lineage table without any ownership check.
PoC
Prerequisites: ML
⚡ Watch CVE-2026-69146
Get an email if CVE-2026-69146 is added to CISA KEV, gains public exploit code, or a new advisory cites it — max one per day, one-click unsubscribe.
Exploitation outlook
- Low exploitation risk0.22% 30-day exploitation probability — currently an unlikely target, but scores change as exploit code circulates. Riskier than 12% of all EPSS-scored CVEs.
Advisory coverage (2)
External references
Embed the live status
— this badge updates automatically when the KEV or exploit status changes. How to embed it →
[](https://www.csirts.com/cve/CVE-2026-69146)