Skip to content

Commit e5659d4

Browse files
committed
Fix properly treating different UNIX socket paths as different origins
Fixes #2069
1 parent 8224769 commit e5659d4

File tree

3 files changed

+66
-2
lines changed

3 files changed

+66
-2
lines changed

source/core/index.ts

Lines changed: 7 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -32,7 +32,7 @@ import Options, {
3232
} from './options.js';
3333
import {isResponseOk, type PlainResponse, type Response} from './response.js';
3434
import isClientRequest from './utils/is-client-request.js';
35-
import isUnixSocketURL from './utils/is-unix-socket-url.js';
35+
import isUnixSocketURL, {getUnixSocketPath} from './utils/is-unix-socket-url.js';
3636
import {
3737
RequestError,
3838
ReadError,
@@ -831,7 +831,12 @@ export default class Request extends Duplex implements RequestEvents<Request> {
831831
}
832832

833833
// Redirecting to a different site, clear sensitive data.
834-
if (redirectUrl.hostname !== (url as URL).hostname || redirectUrl.port !== (url as URL).port) {
834+
// For UNIX sockets, different socket paths are also different origins.
835+
const isDifferentOrigin = redirectUrl.hostname !== (url as URL).hostname
836+
|| redirectUrl.port !== (url as URL).port
837+
|| getUnixSocketPath(url as URL) !== getUnixSocketPath(redirectUrl);
838+
839+
if (isDifferentOrigin) {
835840
if ('host' in updatedOptions.headers) {
836841
delete updatedOptions.headers.host;
837842
}

source/core/utils/is-unix-socket-url.ts

Lines changed: 23 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -2,3 +2,26 @@
22
export default function isUnixSocketURL(url: URL) {
33
return url.protocol === 'unix:' || url.hostname === 'unix';
44
}
5+
6+
/**
7+
Extract the socket path from a UNIX socket URL.
8+
9+
@example
10+
```
11+
getUnixSocketPath(new URL('http://unix/foo:/path'));
12+
//=> '/foo'
13+
14+
getUnixSocketPath(new URL('unix:/foo:/path'));
15+
//=> '/foo'
16+
17+
getUnixSocketPath(new URL('http://example.com'));
18+
//=> undefined
19+
```
20+
*/
21+
export function getUnixSocketPath(url: URL): string | undefined {
22+
if (!isUnixSocketURL(url)) {
23+
return undefined;
24+
}
25+
26+
return /(?<socketPath>.+?):(?<path>.+)/.exec(`${url.pathname}${url.search}`)?.groups?.socketPath;
27+
}

test/get-unix-socket-path.ts

Lines changed: 36 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,36 @@
1+
import test from 'ava';
2+
import {getUnixSocketPath} from '../source/core/utils/is-unix-socket-url.js';
3+
4+
test('returns socket path for unix: protocol URLs', t => {
5+
const url = new URL('unix:/foo/bar.sock:/path');
6+
t.is(getUnixSocketPath(url), '/foo/bar.sock');
7+
});
8+
9+
test('returns socket path for http://unix URLs', t => {
10+
const url = new URL('http://unix/foo/bar.sock:/path');
11+
t.is(getUnixSocketPath(url), '/foo/bar.sock');
12+
});
13+
14+
test('returns different socket paths for different sockets', t => {
15+
const url1 = new URL('http://unix/tmp/socket1:/path');
16+
const url2 = new URL('http://unix/tmp/socket2:/path');
17+
18+
t.is(getUnixSocketPath(url1), '/tmp/socket1');
19+
t.is(getUnixSocketPath(url2), '/tmp/socket2');
20+
t.not(getUnixSocketPath(url1), getUnixSocketPath(url2));
21+
});
22+
23+
test('returns undefined for regular HTTP URLs', t => {
24+
const url = new URL('http://example.com/path');
25+
t.is(getUnixSocketPath(url), undefined);
26+
});
27+
28+
test('returns undefined for HTTPS URLs', t => {
29+
const url = new URL('https://example.com/path');
30+
t.is(getUnixSocketPath(url), undefined);
31+
});
32+
33+
test('handles socket paths with special characters', t => {
34+
const url = new URL('http://unix/tmp/my-app.sock:/api/endpoint');
35+
t.is(getUnixSocketPath(url), '/tmp/my-app.sock');
36+
});

0 commit comments

Comments
 (0)