mirror of
https://github.com/OutlineFoundation/outline-server.git
synced 2026-10-21 12:00:57 +00:00
fix(server): restrict metrics redirects to trusted origin
This commit is contained in:
parent
5c81fd83ac
commit
005fecd952
1 changed files with 18 additions and 2 deletions
|
|
@ -24,6 +24,8 @@ export async function requestFollowRedirectsWithSameMethodAndBody(
|
|||
url: string,
|
||||
options: RequestInit
|
||||
): Promise<Response> {
|
||||
let currentUrl = new URL(url);
|
||||
let allowedOrigin = currentUrl.origin;
|
||||
// Make a copy of options to modify parameters.
|
||||
const manualRedirectOptions = {
|
||||
...options,
|
||||
|
|
@ -42,7 +44,10 @@ export async function requestFollowRedirectsWithSameMethodAndBody(
|
|||
abort();
|
||||
}
|
||||
try {
|
||||
const response = await fetch(url, {...manualRedirectOptions, signal: controller.signal});
|
||||
const response = await fetch(currentUrl.toString(), {
|
||||
...manualRedirectOptions,
|
||||
signal: controller.signal,
|
||||
});
|
||||
if (![301, 302, 303, 307, 308].includes(response.status)) {
|
||||
const body = response.body as Readable;
|
||||
body.once('end', detach);
|
||||
|
|
@ -57,7 +62,18 @@ export async function requestFollowRedirectsWithSameMethodAndBody(
|
|||
if (!location) {
|
||||
throw new Error('Redirect response is missing a Location header');
|
||||
}
|
||||
url = new URL(location, url).toString();
|
||||
const redirectUrl = new URL(location, currentUrl);
|
||||
const isHttpsUpgrade =
|
||||
currentUrl.protocol === 'http:' &&
|
||||
redirectUrl.protocol === 'https:' &&
|
||||
redirectUrl.hostname === currentUrl.hostname;
|
||||
if (redirectUrl.origin !== allowedOrigin && !isHttpsUpgrade) {
|
||||
throw new Error('Cross-origin redirects are not allowed');
|
||||
}
|
||||
if (isHttpsUpgrade) {
|
||||
allowedOrigin = redirectUrl.origin;
|
||||
}
|
||||
currentUrl = redirectUrl;
|
||||
} catch (error) {
|
||||
abort();
|
||||
throw error;
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue