-
-
Notifications
You must be signed in to change notification settings - Fork 762
fix: update redirect handler options handling, docs, tests #4377
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Changes from all commits
39e870f
5a7053a
4a5c250
8d87bd5
55218cc
b74f1a1
971cc6e
File filter
Filter by extension
Conversations
Jump to
Diff view
Diff view
There are no files selected for viewing
| Original file line number | Diff line number | Diff line change |
|---|---|---|
|
|
@@ -2,17 +2,17 @@ | |
|
|
||
| const RedirectHandler = require('../handler/redirect-handler') | ||
|
|
||
| function createRedirectInterceptor ({ maxRedirections: defaultMaxRedirections } = {}) { | ||
| function createRedirectInterceptor ({ maxRedirections: defaultMaxRedirections, throwOnMaxRedirections: defaultThrowOnMaxRedirections } = {}) { | ||
|
Member
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. This would also need to handle throwOnMaxRedirects.
Author
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Do you mean I can add
Contributor
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Current status, as I understand it:
With those pieces out of the way, I think this PR may be worth reopening. |
||
| return (dispatch) => { | ||
| return function Intercept (opts, handler) { | ||
| const { maxRedirections = defaultMaxRedirections, ...rest } = opts | ||
| const { maxRedirections = defaultMaxRedirections, throwOnMaxRedirections = defaultThrowOnMaxRedirections, ...rest } = opts | ||
|
|
||
| if (maxRedirections == null || maxRedirections === 0) { | ||
| return dispatch(opts, handler) | ||
| } | ||
|
|
||
| const dispatchOpts = { ...rest } // Stop sub dispatcher from also redirecting. | ||
| const redirectHandler = new RedirectHandler(dispatch, maxRedirections, dispatchOpts, handler) | ||
| const redirectHandler = new RedirectHandler(dispatch, maxRedirections, { throwOnMaxRedirections, ...dispatchOpts }, handler) | ||
|
Author
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Maybe a little confusing that |
||
| return dispatch(dispatchOpts, redirectHandler) | ||
| } | ||
| } | ||
|
|
||
| Original file line number | Diff line number | Diff line change |
|---|---|---|
|
|
@@ -23,23 +23,23 @@ const { | |
| } = undici | ||
|
|
||
| for (const factory of [ | ||
| (server, opts) => | ||
| new undici.Agent(opts).compose( | ||
| redirect({ maxRedirections: opts?.maxRedirections }) | ||
| (server, dispatchOpts) => | ||
| new undici.Agent(dispatchOpts).compose( | ||
| redirect({ maxRedirections: dispatchOpts?.maxRedirections, throwOnMaxRedirections: dispatchOpts?.throwOnMaxRedirections }) | ||
|
Author
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. I think there could even be another arg,
Collaborator
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. i like this idea, but likely should go in a separate PR 👍 |
||
| ), | ||
| (server, opts) => | ||
| new undici.Pool(`http://${server}`, opts).compose( | ||
| redirect({ maxRedirections: opts?.maxRedirections }) | ||
| (server, dispatchOpts) => | ||
| new undici.Pool(`http://${server}`, dispatchOpts).compose( | ||
| redirect({ maxRedirections: dispatchOpts?.maxRedirections, throwOnMaxRedirections: dispatchOpts?.throwOnMaxRedirections }) | ||
| ), | ||
| (server, opts) => | ||
| new undici.Client(`http://${server}`, opts).compose( | ||
| redirect({ maxRedirections: opts?.maxRedirections }) | ||
| (server, dispatchOpts) => | ||
| new undici.Client(`http://${server}`, dispatchOpts).compose( | ||
| redirect({ maxRedirections: dispatchOpts?.maxRedirections, throwOnMaxRedirections: dispatchOpts?.throwOnMaxRedirections }) | ||
| ) | ||
| ]) { | ||
| const request = (t, server, opts, ...args) => { | ||
| const dispatcher = factory(server, opts) | ||
| const request = (t, server, dispatchOpts, url, requestOpts) => { | ||
| const dispatcher = factory(server, dispatchOpts) | ||
| after(() => dispatcher.close()) | ||
| return undici.request(args[0], { ...args[1], dispatcher }, args[2]) | ||
|
Author
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more.
|
||
| return undici.request(url, { ...requestOpts, dispatcher }) | ||
| } | ||
|
|
||
| test('should always have a history with the final URL even if no redirections were followed', async t => { | ||
|
|
@@ -445,7 +445,7 @@ for (const factory of [ | |
| await t.completed | ||
| }) | ||
|
|
||
| test('should follow a redirect chain up to the allowed number of times for redirectionLimitReached', async t => { | ||
| test('should follow a redirect chain up to the allowed number of times for maxRedirections using the undici.request opts and undocumented throwOnMaxRedirect', async t => { | ||
| t = tspl(t, { plan: 1 }) | ||
|
|
||
| const server = await startRedirectingServer() | ||
|
|
@@ -466,6 +466,48 @@ for (const factory of [ | |
| await t.completed | ||
| }) | ||
|
|
||
| test('should follow a redirect chain up to the allowed number of times for maxRedirections using the undici.request opts', async t => { | ||
| t = tspl(t, { plan: 1 }) | ||
|
|
||
| const server = await startRedirectingServer() | ||
|
|
||
| try { | ||
| await request(t, server, undefined, `http://${server}/300`, { | ||
| maxRedirections: 2, | ||
| throwOnMaxRedirections: true | ||
| }) | ||
| } catch (error) { | ||
| if (error.message.startsWith('max redirects')) { | ||
| t.ok(true, 'Max redirects handled correctly') | ||
| } else { | ||
| t.fail(`Unexpected error: ${error.message}`) | ||
| } | ||
| } | ||
|
|
||
| await t.completed | ||
| }) | ||
|
|
||
| test('should follow a redirect chain up to the allowed number of times for maxRedirections using the dispatch opts', async t => { | ||
| t = tspl(t, { plan: 1 }) | ||
|
|
||
| const server = await startRedirectingServer() | ||
|
|
||
| try { | ||
| await request(t, server, { | ||
| maxRedirections: 2, | ||
| throwOnMaxRedirections: true | ||
| }, `http://${server}/300`, undefined) | ||
| } catch (error) { | ||
| if (error.message.startsWith('max redirects')) { | ||
| t.ok(true, 'Max redirects handled correctly') | ||
| } else { | ||
| t.fail(`Unexpected error: ${error.message}`) | ||
| } | ||
| } | ||
|
|
||
| await t.completed | ||
| }) | ||
|
|
||
| test('when a Location response header is NOT present', async t => { | ||
| t = tspl(t, { plan: 6 * 3 }) | ||
|
|
||
|
|
||
| Original file line number | Diff line number | Diff line change |
|---|---|---|
|
|
@@ -8,7 +8,7 @@ export default Interceptors | |
| declare namespace Interceptors { | ||
| export type DumpInterceptorOpts = { maxSize?: number } | ||
| export type RetryInterceptorOpts = RetryHandler.RetryOptions | ||
| export type RedirectInterceptorOpts = { maxRedirections?: number } | ||
| export type RedirectInterceptorOpts = { maxRedirections?: number, throwOnMaxRedirections?: boolean } | ||
|
Author
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Probably worth defining |
||
|
|
||
| export type ResponseErrorInterceptorOpts = { throwOnError: boolean } | ||
| export type CacheInterceptorOpts = CacheHandler.CacheOptions | ||
|
|
||
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Please keep both name around but document only the new one
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Thanks @mcollina. That makes sense to me. Restored
throwOnMaxRedirectand its tests in 971cc6e