-
Notifications
You must be signed in to change notification settings - Fork 1
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
- Loading branch information
1 parent
d2772e1
commit 0760eae
Showing
4 changed files
with
122 additions
and
11 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
|
@@ -12,7 +12,7 @@ import { | |
ResponseJSONParseError, ApiCallParametersWithPagination, PageResult, | ||
} from '../api'; | ||
import fetch, { Response, Headers } from 'node-fetch'; | ||
import { buildErrorContext, manageExpiredToken } from './api-client-helpers'; | ||
import { buildErrorContext, manageExpiredToken, reviveDates } from './api-client-helpers'; | ||
import { | ||
buildPaginationContext, | ||
calculateNextPage, | ||
|
@@ -94,8 +94,8 @@ export class ApiFetchClient extends ApiClient { | |
throw exception; | ||
} | ||
|
||
// If everything went fine, we return the transformed API response | ||
return transformedResponse; | ||
// If everything went fine, we apply a last transformation to revive the dates, and we return the transformed API response | ||
return reviveDates(transformedResponse); | ||
} | ||
|
||
private async sinchFetch( | ||
|
@@ -125,13 +125,15 @@ export class ApiFetchClient extends ApiClient { | |
const errorContext: ErrorContext = buildErrorContext(props, origin); | ||
|
||
// Execute call | ||
return this.sinchFetchWithPagination<T>(props, errorContext); | ||
return this.sinchFetchWithPagination<T>(props, errorContext, origin); | ||
}; | ||
|
||
private async sinchFetchWithPagination<T>( | ||
apiCallParameters: ApiCallParametersWithPagination, | ||
errorContext: ErrorContext, | ||
origin: string | null, | ||
): Promise<PageResult<T>> { | ||
let exception: Error | undefined; | ||
const response = await fetch(apiCallParameters.url, apiCallParameters.requestOptions); | ||
if ( | ||
response.status === 401 | ||
|
@@ -146,14 +148,46 @@ export class ApiFetchClient extends ApiClient { | |
} | ||
// When handling pagination, we won't return the raw response but a PageResult | ||
const body = await response.text(); | ||
const result = JSON.parse(body); | ||
let result; | ||
try { | ||
// Try to parse the body if there is one | ||
result = body ? JSON.parse(body) : undefined; | ||
} catch (error: any) { | ||
exception = new ResponseJSONParseError( | ||
error.message || 'Fail to parse response body', | ||
(response && response.status) || 0, | ||
errorContext, | ||
body, | ||
); | ||
} | ||
|
||
// Load and invoke the response plugins to transform the response | ||
const responsePlugins = this.loadResponsePlugins( | ||
this.apiClientOptions.responsePlugins, | ||
apiCallParameters, | ||
response, | ||
exception, | ||
origin); | ||
let transformedResponse = result; | ||
for (const pluginRunner of responsePlugins) { | ||
transformedResponse = await pluginRunner.transform(transformedResponse); | ||
} | ||
|
||
// Revive Date objects | ||
transformedResponse = reviveDates(transformedResponse); | ||
This comment has been minimized.
Sorry, something went wrong.
This comment has been minimized.
Sorry, something went wrong.
asein-sinch
Author
Collaborator
|
||
|
||
// If there has been an error at some point in the process, throw it | ||
if (exception) { | ||
throw exception; | ||
} | ||
|
||
// Read the elements' array with its key | ||
const responseData: Array<T> = result[apiCallParameters.dataKey]; | ||
const responseData: Array<T> = transformedResponse[apiCallParameters.dataKey]; | ||
// Build the PageResult object | ||
const nextPage = calculateNextPage(result, buildPaginationContext(apiCallParameters)); | ||
const nextPage = JSON.stringify(calculateNextPage(transformedResponse, buildPaginationContext(apiCallParameters))); | ||
return { | ||
data: responseData || [], | ||
hasNextPage: hasMore(result, buildPaginationContext(apiCallParameters)), | ||
hasNextPage: hasMore(transformedResponse, buildPaginationContext(apiCallParameters)), | ||
nextPageValue: nextPage, | ||
nextPage: () => createNextPageMethod<T>( | ||
this, buildPaginationContext(apiCallParameters), apiCallParameters.requestOptions, nextPage), | ||
|
47 changes: 47 additions & 0 deletions
47
packages/sdk-client/tests/client/api-client-helpers.test.ts
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,47 @@ | ||
import { reviveDates } from '../../src/client/api-client-helpers'; | ||
|
||
describe('API client helpers', () => { | ||
|
||
it('should revive Dates', () => { | ||
const obj = { | ||
date1: '2024-01-31T12:00:00.000Z', | ||
nested: { | ||
date2: '2024-02-15T18:30:00.000Z', | ||
}, | ||
array: [ | ||
{ | ||
date3: '2024-02-03T04:15:00.000Z', | ||
}, | ||
{ | ||
date3: '2024-02-04T20:22:00.123Z', | ||
}, | ||
], | ||
otherProp: 'otherValue', | ||
otherNumber: 0, | ||
otherBoolean: true, | ||
otherUndefined: undefined, | ||
otherNull: null, | ||
}; | ||
const expected = { | ||
date1: new Date('2024-01-31T12:00:00.000Z'), | ||
nested: { | ||
date2: new Date('2024-02-15T18:30:00.000Z'), | ||
}, | ||
array: [ | ||
{ | ||
date3: new Date('2024-02-03T04:15:00.000Z'), | ||
}, | ||
{ | ||
date3: new Date('2024-02-04T20:22:00.123Z'), | ||
}, | ||
], | ||
otherProp: 'otherValue', | ||
otherNumber: 0, | ||
otherBoolean: true, | ||
otherUndefined: undefined, | ||
otherNull: null, | ||
}; | ||
expect(reviveDates(obj)).toStrictEqual(expected); | ||
}); | ||
|
||
}); |
What about string date representation without timezone ?
is there conflicts between general usage/parsing here and dedicated case where received date do not contains it (the timezone) and we need to fix value before transformation to Date ?