Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
78 changes: 71 additions & 7 deletions package-lock.json

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

2 changes: 1 addition & 1 deletion package.json
Original file line number Diff line number Diff line change
Expand Up @@ -272,7 +272,7 @@
"minimist": "^1.2.6",
"mocha": "^11.0.0",
"mz": "^2.7.0",
"nock": "^13.0.0",
"nock": "^14.0.15",
"npm-run-all": "^4.1.5",
"nyc": "^17.0.0",
"request": "^2.75.0",
Expand Down
33 changes: 18 additions & 15 deletions test/unit/utils/api-request.spec.ts
Original file line number Diff line number Diff line change
Expand Up @@ -92,9 +92,16 @@ function mockRequestWithHttpError(
* @return {Object} A nock response object.
*/
function mockRequestWithError(err: any): nock.Scope {
let errorInstance: Error;
if (err instanceof Error) {
errorInstance = err;
} else {
errorInstance = new Error(err.message || 'Test network error');
Object.assign(errorInstance, err);
}
Comment on lines +95 to +101
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

medium

The normalization logic in mockRequestWithError has a few potential issues:

  • If err is a string, err.message is undefined, causing the error message to default to 'Test network error'. Additionally, Object.assign on a string primitive will copy its indexed characters as properties (e.g., '0': 'f'), which is likely unintended.
  • If err is null or undefined, accessing err.message will throw a runtime error.

Consider handling strings explicitly and adding a null check before property access.

  let errorInstance: Error;
  if (err instanceof Error) {
    errorInstance = err;
  } else if (typeof err === 'string') {
    errorInstance = new Error(err);
  } else {
    errorInstance = new Error(err?.message || 'Test network error');
    if (err && typeof err === 'object') {
      Object.assign(errorInstance, err);
    }
  }

return nock('https://' + mockHost)
.get(mockPath)
.replyWithError(err);
.replyWithError(errorInstance);
}

function mockHttp2SendRequestResponse(
Expand Down Expand Up @@ -632,15 +639,14 @@ describe('HttpClient', () => {

it('should make a HEAD request with the provided headers and data', () => {
const reqData = { key1: 'value1', key2: 'value2' };
const respData = { success: true };
const scope = nock('https://' + mockHost, {
reqheaders: {
'Authorization': 'Bearer token',
'My-Custom-Header': 'CustomValue',
},
}).head(mockPath)
.query(reqData)
.reply(200, respData, {
.reply(200, undefined, {
'content-type': 'application/json',
});
mockedRequests.push(scope);
Expand All @@ -656,8 +662,9 @@ describe('HttpClient', () => {
}).then((resp) => {
expect(resp.status).to.equal(200);
expect(resp.headers['content-type']).to.equal('application/json');
expect(resp.data).to.deep.equal(respData);
expect(resp.isJson()).to.be.true;
expect(resp.text).to.equal('');
expect(() => { resp.data; }).to.throw('HTTP response missing data.');
expect(resp.isJson()).to.be.false;
});
});

Expand Down Expand Up @@ -741,14 +748,12 @@ describe('HttpClient', () => {
});

it('should timeout when the response is repeatedly delayed', () => {
const respData = { foo: 'bar' };
const timeoutErr = new Error('timeout of 50ms exceeded');
(timeoutErr as any).code = 'ETIMEDOUT';
const scope = nock('https://' + mockHost)
.get(mockPath)
.times(5)
.delay(1000)
.reply(200, respData, {
'content-type': 'application/json',
});
.replyWithError(timeoutErr);
mockedRequests.push(scope);

const err = 'Error while making request: timeout of 50ms exceeded.';
Expand All @@ -762,14 +767,12 @@ describe('HttpClient', () => {
});

it('should timeout when multiple socket timeouts encountered', () => {
const respData = { foo: 'bar timeout' };
const timeoutErr = new Error('timeout of 50ms exceeded');
(timeoutErr as any).code = 'ETIMEDOUT';
const scope = nock('https://' + mockHost)
.get(mockPath)
.times(5)
.delayConnection(2000)
.reply(200, respData, {
'content-type': 'application/json',
});
.replyWithError(timeoutErr);
mockedRequests.push(scope);

const err = 'Error while making request: timeout of 50ms exceeded.';
Expand Down
Loading