@@ -25,7 +25,7 @@ export interface IWebClientResponseBase {
2525}
2626
2727/**
28- * For use with {@link WebClient}.
28+ * A response from {@link WebClient.fetchAsync }.
2929 */
3030export interface IWebClientResponse extends IWebClientResponseBase {
3131 getTextAsync : ( ) => Promise < string > ;
@@ -117,7 +117,7 @@ function _makeRawRequestAsync<TResponse>(
117117 resolve : ( result : TResponse | PromiseLike < TResponse > ) => void ,
118118 reject : ( error : Error ) => void
119119 ) => void ,
120- selfFn : ( url : string , options : IRequestOptions , isRedirect ?: boolean ) => Promise < TResponse >
120+ requestFnAsync : ( url : string , options : IRequestOptions , isRedirect ?: boolean ) => Promise < TResponse >
121121) : Promise < TResponse > {
122122 const { body, redirect } = options ;
123123
@@ -128,25 +128,25 @@ function _makeRawRequestAsync<TResponse>(
128128 parsedUrl . protocol === 'https:' ? httpsRequest : httpRequest ;
129129
130130 const req : ClientRequest = requestFunction ( url , options , ( response : IncomingMessage ) => {
131- const statusCode : number | undefined = response . statusCode ;
132-
131+ const {
132+ statusCode,
133+ headers : { location : redirectUrl }
134+ } = response ;
133135 if ( statusCode === 301 || statusCode === 302 ) {
134136 // Drain the redirect response before following
135137 response . resume ( ) ;
136138 switch ( redirect ) {
137139 case 'follow' : {
138- const redirectUrl : string | string [ ] | undefined = response . headers . location ;
139- if ( typeof redirectUrl === 'string' ) {
140- resolve ( selfFn ( redirectUrl , options , true ) ) ;
140+ if ( redirectUrl ) {
141+ requestFnAsync ( redirectUrl , options , true ) . then ( resolve ) . catch ( reject ) ;
141142 } else {
142- reject (
143- new Error ( `Received status code ${ response . statusCode } with no location header: ${ url } ` )
144- ) ;
143+ reject ( new Error ( `Received status code ${ statusCode } with no location header: ${ url } ` ) ) ;
145144 }
146145 return ;
147146 }
147+
148148 case 'error' :
149- reject ( new Error ( `Received status code ${ response . statusCode } : ${ url } ` ) ) ;
149+ reject ( new Error ( `Received status code ${ statusCode } : ${ url } ` ) ) ;
150150 return ;
151151 }
152152 }
@@ -188,10 +188,8 @@ const makeRequestAsync: FetchFn = async (
188188 responseBuffers . push ( Buffer . from ( chunk ) ) ;
189189 } ) ;
190190 response . on ( 'end' , ( ) => {
191+ const { statusCode : status = 0 , statusMessage : statusText , headers } = response ;
191192 const responseData : Buffer = Buffer . concat ( responseBuffers ) ;
192- const status : number = response . statusCode || 0 ;
193- const statusText : string | undefined = response . statusMessage ;
194- const headers : Record < string , string | string [ ] | undefined > = response . headers ;
195193
196194 let bodyString : string | undefined ;
197195 let bodyJson : unknown | undefined ;
@@ -285,10 +283,7 @@ const makeStreamRequestAsync: StreamFetchFn = async (
285283 wasRedirected : boolean ,
286284 resolve : ( result : IWebClientStreamResponse | PromiseLike < IWebClientStreamResponse > ) => void
287285 ) : void => {
288- const status : number = response . statusCode || 0 ;
289- const statusText : string | undefined = response . statusMessage ;
290- const headers : Record < string , string | string [ ] | undefined > = response . headers ;
291-
286+ const { statusCode : status = 0 , statusMessage : statusText , headers } = response ;
292287 resolve ( {
293288 ok : status >= 200 && status < 300 ,
294289 status,
@@ -306,8 +301,8 @@ const makeStreamRequestAsync: StreamFetchFn = async (
306301 * A helper for issuing HTTP requests.
307302 */
308303export class WebClient {
309- private static _requestFn : FetchFn = makeRequestAsync ;
310- private static _streamRequestFn : StreamFetchFn = makeStreamRequestAsync ;
304+ private static _requestFnAsync : FetchFn = makeRequestAsync ;
305+ private static _streamRequestFnAsync : StreamFetchFn = makeStreamRequestAsync ;
311306
312307 public readonly standardHeaders : Record < string , string > = { } ;
313308
@@ -317,19 +312,19 @@ export class WebClient {
317312 public proxy : WebClientProxy = WebClientProxy . Detect ;
318313
319314 public static mockRequestFn ( fn : FetchFn ) : void {
320- WebClient . _requestFn = fn ;
315+ WebClient . _requestFnAsync = fn ;
321316 }
322317
323318 public static resetMockRequestFn ( ) : void {
324- WebClient . _requestFn = makeRequestAsync ;
319+ WebClient . _requestFnAsync = makeRequestAsync ;
325320 }
326321
327322 public static mockStreamRequestFn ( fn : StreamFetchFn ) : void {
328- WebClient . _streamRequestFn = fn ;
323+ WebClient . _streamRequestFnAsync = fn ;
329324 }
330325
331326 public static resetMockStreamRequestFn ( ) : void {
332- WebClient . _streamRequestFn = makeStreamRequestAsync ;
327+ WebClient . _streamRequestFnAsync = makeStreamRequestAsync ;
333328 }
334329
335330 public static mergeHeaders ( target : Record < string , string > , source : Record < string , string > ) : void {
@@ -347,8 +342,8 @@ export class WebClient {
347342 url : string ,
348343 options ?: IGetFetchOptions | IFetchOptionsWithBody
349344 ) : Promise < IWebClientResponse > {
350- const requestInit : IRequestOptions = buildRequestOptions ( this , options ) ;
351- return await WebClient . _requestFn ( url , requestInit ) ;
345+ const requestInit : IRequestOptions = this . _buildRequestOptions ( options ) ;
346+ return await WebClient . _requestFnAsync ( url , requestInit ) ;
352347 }
353348
354349 /**
@@ -359,71 +354,70 @@ export class WebClient {
359354 url : string ,
360355 options ?: IGetFetchOptions | IFetchOptionsWithBody
361356 ) : Promise < IWebClientStreamResponse > {
362- const requestInit : IRequestOptions = buildRequestOptions ( this , options ) ;
363- return await WebClient . _streamRequestFn ( url , requestInit ) ;
357+ const requestInit : IRequestOptions = this . _buildRequestOptions ( options ) ;
358+ return await WebClient . _streamRequestFnAsync ( url , requestInit ) ;
364359 }
365- }
366360
367- function buildRequestOptions (
368- client : WebClient ,
369- options ?: IGetFetchOptions | IFetchOptionsWithBody
370- ) : IRequestOptions {
371- const {
372- headers : optionsHeaders ,
373- timeoutMs = 15 * 1000 ,
374- verb,
375- redirect,
376- body,
377- noDecode
378- } = ( options as IFetchOptionsWithBody | undefined ) ?? { } ;
379-
380- const headers : Record < string , string > = { } ;
381-
382- WebClient . mergeHeaders ( headers , client . standardHeaders ) ;
383-
384- if ( optionsHeaders ) {
385- WebClient . mergeHeaders ( headers , optionsHeaders ) ;
386- }
361+ private _buildRequestOptions ( options ?: IGetFetchOptions | IFetchOptionsWithBody ) : IRequestOptions {
362+ const {
363+ headers : optionsHeaders ,
364+ timeoutMs = 15 * 1000 ,
365+ verb,
366+ redirect,
367+ body,
368+ noDecode
369+ } = ( options as IFetchOptionsWithBody | undefined ) ?? { } ;
387370
388- if ( client . userAgent ) {
389- headers [ USER_AGENT_HEADER_NAME ] = client . userAgent ;
390- }
371+ const headers : Record < string , string > = { } ;
391372
392- if ( client . accept ) {
393- headers [ ACCEPT_HEADER_NAME ] = client . accept ;
394- }
373+ const { standardHeaders, userAgent, accept, proxy } = this ;
395374
396- let proxyUrl : string = '' ;
375+ WebClient . mergeHeaders ( headers , standardHeaders ) ;
397376
398- switch ( client . proxy ) {
399- case WebClientProxy . Detect :
400- if ( process . env . HTTPS_PROXY ) {
401- proxyUrl = process . env . HTTPS_PROXY ;
402- } else if ( process . env . HTTP_PROXY ) {
403- proxyUrl = process . env . HTTP_PROXY ;
404- }
405- break ;
406-
407- case WebClientProxy . Fiddler :
408- // For debugging, disable cert validation
409- // eslint-disable-next-line
410- process . env [ 'NODE_TLS_REJECT_UNAUTHORIZED' ] = '0' ;
411- proxyUrl = 'http://localhost:8888/' ;
412- break ;
413- }
377+ if ( optionsHeaders ) {
378+ WebClient . mergeHeaders ( headers , optionsHeaders ) ;
379+ }
414380
415- let agent : HttpAgent | undefined = undefined ;
416- if ( proxyUrl ) {
417- agent = createHttpsProxyAgent ( proxyUrl ) ;
418- }
381+ if ( userAgent ) {
382+ headers [ USER_AGENT_HEADER_NAME ] = userAgent ;
383+ }
384+
385+ if ( accept ) {
386+ headers [ ACCEPT_HEADER_NAME ] = accept ;
387+ }
388+
389+ let proxyUrl : string = '' ;
419390
420- return {
421- method : verb ,
422- headers,
423- agent,
424- timeout : timeoutMs ,
425- redirect,
426- body,
427- noDecode
428- } ;
391+ switch ( proxy ) {
392+ case WebClientProxy . Detect :
393+ if ( process . env . HTTPS_PROXY ) {
394+ proxyUrl = process . env . HTTPS_PROXY ;
395+ } else if ( process . env . HTTP_PROXY ) {
396+ proxyUrl = process . env . HTTP_PROXY ;
397+ }
398+ break ;
399+
400+ case WebClientProxy . Fiddler :
401+ // For debugging, disable cert validation
402+ // eslint-disable-next-line
403+ process . env [ 'NODE_TLS_REJECT_UNAUTHORIZED' ] = '0' ;
404+ proxyUrl = 'http://localhost:8888/' ;
405+ break ;
406+ }
407+
408+ let agent : HttpAgent | undefined = undefined ;
409+ if ( proxyUrl ) {
410+ agent = createHttpsProxyAgent ( proxyUrl ) ;
411+ }
412+
413+ return {
414+ method : verb ,
415+ headers,
416+ agent,
417+ timeout : timeoutMs ,
418+ redirect,
419+ body,
420+ noDecode
421+ } ;
422+ }
429423}
0 commit comments