Skip to content

Commit c27a53a

Browse files
Mnkrasalexghr
andauthored
fix: Allow prefixUrl to work (#370)
* fix: Allow prefixUrl to work * Add back ability to merge queryParams Co-authored-by: Alex Gherghisan <alexghr@users.noreply.github.com> * Changes per feedback --------- Co-authored-by: Alex Gherghisan <alexghr@users.noreply.github.com>
1 parent 1774779 commit c27a53a

File tree

3 files changed

+64
-20
lines changed

3 files changed

+64
-20
lines changed

src/lib/fetch.ts

Lines changed: 29 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -11,7 +11,33 @@ export function createFetch(got: Got): GotFetch {
1111
const globalCache = new Map();
1212

1313
return async (input, opts) => {
14-
const url = new URL(typeof input === 'string' ? input : input.url);
14+
let url = input.toString();
15+
let searchParams: URLSearchParams = new URLSearchParams();
16+
17+
try {
18+
const urlObj = new URL(
19+
typeof input === "string"
20+
? input
21+
: input.url
22+
);
23+
24+
searchParams = new URLSearchParams(urlObj.searchParams);
25+
urlObj.search = "";
26+
27+
url = urlObj.href;
28+
} catch (e) {
29+
// Ignore url parsing failure, likely prefixUrl is being used
30+
// When using prefixUrl, the path cannot start with a "/"
31+
if (url.startsWith("/")) {
32+
url = url.substring(1);
33+
}
34+
35+
if (url.includes("?")) {
36+
const [path, search] = url.split("?");
37+
url = path;
38+
searchParams = new URLSearchParams(search);
39+
}
40+
}
1541
const request: RequestInit = typeof input === 'object' ? input : opts || {};
1642

1743
if (request.mode === 'no-cors' || request.mode === 'same-origin' || request.mode === 'navigate') {
@@ -31,18 +57,10 @@ export function createFetch(got: Got): GotFetch {
3157
throw new TypeError(format('request.headers must be plain object: %j', request.headers));
3258
}
3359

34-
// got does not merge base searchParams with the url's searchParams
35-
// but it does merge searchParams options
36-
// so we clone the url's searchParams
37-
// we also clear the url's search to work around this bug
38-
// https://github.com/sindresorhus/got/issues/1188
39-
const searchParams = new URLSearchParams(url.searchParams);
40-
url.search = '';
41-
4260
const gotOpts: GotOptions = {
4361
// url needs to be stringified to support UNIX domain sockets, and
4462
// For more info see https://github.com/alexghr/got-fetch/pull/8
45-
url: url.toString(),
63+
url,
4664
searchParams,
4765
followRedirect: true,
4866
throwHttpErrors: false,
@@ -107,7 +125,7 @@ export function createFetch(got: Got): GotFetch {
107125
// using Array.prototype.at would've been nice but it's not
108126
// supported by anything below Node 16.8
109127
? r.redirectUrls[r.redirectUrls.length - 1]
110-
: url.href,
128+
: r.url,
111129
});
112130
});
113131
}

src/test/fetch.request.test.ts

Lines changed: 34 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -2,7 +2,7 @@ import got from 'got';
22
import { URLSearchParams } from 'url';
33

44
import { createFetch } from '../lib/fetch';
5-
import { Interceptor, intercept, assert200, url } from './util';
5+
import { Interceptor, intercept, assert200, url, ORIGIN } from './util';
66

77
describe('fetch request', () => {
88
let interceptor: Interceptor;
@@ -37,6 +37,18 @@ describe('fetch request', () => {
3737
const fetch = createFetch(got);
3838
await assert200(fetch(url('/foo')));
3939
});
40+
41+
it('allows prefixUrl', async () => {
42+
expect.assertions(1);
43+
interceptor.intercept('/foo', 'get').reply(200);
44+
45+
const prefixedClient = got.extend({
46+
prefixUrl: ORIGIN
47+
})
48+
49+
const fetch = createFetch(prefixedClient);
50+
await assert200(fetch('/foo'));
51+
});
4052
});
4153

4254
describe('querystring', () => {
@@ -48,13 +60,27 @@ describe('fetch request', () => {
4860
await assert200(fetch(url('/', { foo: '123', bar: '456' })));
4961
});
5062

51-
it('merges query string parameters', async () => {
52-
expect.assertions(1);
53-
interceptor.intercept('/', 'get').query({ foo: '123', bar: '456' }).reply(200);
63+
});
5464

55-
const fetch = createFetch(got.extend({ searchParams: { bar: '456' } }));
56-
await assert200(fetch(url('/', { foo: '123' })));
57-
});
65+
it('merges query string parameters', async () => {
66+
expect.assertions(1);
67+
interceptor.intercept('/', 'get').query({ foo: '123', bar: '456' }).reply(200);
68+
69+
const fetch = createFetch(got.extend({ searchParams: { bar: '456' } }));
70+
await assert200(fetch(url('/', { foo: '123' })));
71+
});
72+
73+
it('merges query string parameters with prefixUrl', async () => {
74+
expect.assertions(1);
75+
interceptor.intercept('/foo', 'get').query({ foo: '123', bar: '456' }).reply(200);
76+
77+
const prefixedClient = got.extend({
78+
prefixUrl: ORIGIN,
79+
searchParams: { bar: '456' }
80+
})
81+
82+
const fetch = createFetch(prefixedClient);
83+
await assert200(fetch('/foo?foo=123'));
5884
});
5985

6086
describe('headers', () => {
@@ -175,7 +201,7 @@ describe('fetch request', () => {
175201

176202
});
177203

178-
it.only("sends own content-type header", async () => {
204+
it("sends own content-type header", async () => {
179205
expect.assertions(1);
180206

181207
// as set by the client

src/test/util.ts

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,7 @@
11
import nock from 'nock';
22
import { URL } from 'url';
33

4-
const ORIGIN = 'https://example.com';
4+
export const ORIGIN = 'https://example.com';
55

66
export type Interceptor = nock.Scope;
77
export function intercept(): Interceptor {

0 commit comments

Comments
 (0)