Skip to content

Commit

Permalink
patch(core/url): Throw if VERDACCIO_FORWARDED_PROTO resolves to an ar…
Browse files Browse the repository at this point in the history
…ray (#4613)

* patch(core/url): Throw if VERDACCIO_FORWARDED_PROTO resolves to an array

* changeset
  • Loading branch information
Tobbe committed Jun 2, 2024
1 parent 2bc45c8 commit 38b1e82
Show file tree
Hide file tree
Showing 3 changed files with 38 additions and 1 deletion.
5 changes: 5 additions & 0 deletions .changeset/stupid-dancers-relate.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
---
'@verdaccio/url': patch
---

patch(core/url): Throw if VERDACCIO_FORWARDED_PROTO resolves to an array (#4613 by @Tobbe)
9 changes: 8 additions & 1 deletion packages/core/url/src/index.ts
Original file line number Diff line number Diff line change
Expand Up @@ -121,10 +121,17 @@ export function getPublicUrl(url_prefix: string = '', requestOptions: RequestOpt
throw new Error('invalid host');
}

// 'X-Forwarded-Proto' is the default header
const protoHeader: string =
process.env.VERDACCIO_FORWARDED_PROTO?.toLocaleLowerCase() ??
HEADERS.FORWARDED_PROTO.toLowerCase();
const forwardedProtocolHeaderValue = requestOptions.headers[protoHeader] as string | undefined;
const forwardedProtocolHeaderValue = requestOptions.headers[protoHeader];

if (Array.isArray(forwardedProtocolHeaderValue)) {
// This really should never happen - only set-cookie is allowed to have
// multiple values.
throw new Error('invalid forwarded protocol header value. Reading header ' + protoHeader);
}

const protocol = getWebProtocol(forwardedProtocolHeaderValue, requestOptions.protocol);
const combinedUrl = combineBaseUrl(protocol, host, url_prefix);
Expand Down
25 changes: 25 additions & 0 deletions packages/core/url/tests/getPublicUrl.spec.ts
Original file line number Diff line number Diff line change
Expand Up @@ -316,6 +316,31 @@ describe('env variable', () => {
delete process.env.VERDACCIO_FORWARDED_PROTO;
});

test('with the VERDACCIO_FORWARDED_PROTO environment variable set to "set-cookie"', () => {
process.env.VERDACCIO_FORWARDED_PROTO = 'set-cookie';
const req = httpMocks.createRequest({
method: 'GET',
headers: {
host: 'some.com',
cookie: 'name=value; name2=value2;',
'set-cookie': [
'cookieName1=value; expires=Tue, 19 Jan 2038 03:14:07 GMT;',
'cookieName2=value; expires=Tue, 19 Jan 2038 03:14:07 GMT;',
],
},
url: '/',
});

expect(() =>
getPublicUrl('/test/', {
host: req.hostname,
headers: req.headers as any,
protocol: req.protocol,
})
).toThrow('invalid forwarded protocol header value. Reading header set-cookie');
delete process.env.VERDACCIO_FORWARDED_PROTO;
});

test('with a invalid X-Forwarded-Proto https and host injection with invalid host', () => {
process.env.VERDACCIO_PUBLIC_URL = 'http://injection.test.com"><svg onload="alert(1)">';
const req = httpMocks.createRequest({
Expand Down

0 comments on commit 38b1e82

Please sign in to comment.