diff --git a/src/wrapper.spec.ts b/src/wrapper.spec.ts index 8b5bb9c..4d84b3c 100644 --- a/src/wrapper.spec.ts +++ b/src/wrapper.spec.ts @@ -119,24 +119,45 @@ describe('RequestWrapper', function() { expect(requestArgument.httpsAgent).to.eql(agents.httpsAgent); }); - it('should throw error when response code is 400 or above', async () => { - requestGetStub.restore(); - nock('http://very.host.io:443') - .get('/purchases/1/content') - .reply(400, { replyText: 'Unknown route' }); + context('error responses', () => { + it('should return JSON in EscherRequestError if response data is json parsable', async () => { + requestGetStub.restore(); + nock('http://very.host.io:443') + .get('/purchases/1/content') + .reply(400, { replyText: 'Unknown route' }, { 'Content-Type': 'application/json; charset=utf-8' }); - try { - await wrapper.send(); - throw new Error('Error should have been thrown'); - } catch (err) { - const error = err as EscherRequestError; - expect(error).to.be.an.instanceof(EscherRequestError); - expect(error.message).to.eql('Error in http response (status: 400)'); - expect(error.code).to.eql(400); - expect(error.data).to.eql(JSON.stringify({ replyText: 'Unknown route' })); - } + try { + await wrapper.send(); + throw new Error('Error should have been thrown'); + } catch (err) { + const error = err as EscherRequestError; + expect(error).to.be.an.instanceof(EscherRequestError); + expect(error.message).to.eql('Error in http response (status: 400)'); + expect(error.code).to.eql(400); + expect(error.data).to.eql({ replyText: 'Unknown route' }); + } + }); + + it('should return text and not fail parsing response data if wrong content-type headers are set', async () => { + requestGetStub.restore(); + nock('http://very.host.io:443') + .get('/purchases/1/content') + .reply(500, 'Unexpected Error', { 'Content-Type': 'application/json; charset=utf-8' }); + + try { + await wrapper.send(); + throw new Error('Error should have been thrown'); + } catch (err) { + const error = err as EscherRequestError; + expect(error).to.be.an.instanceof(EscherRequestError); + expect(error.message).to.eql('Error in http response (status: 500)'); + expect(error.code).to.eql(500); + expect(error.data).to.eql('Unexpected Error'); + } + }); }); + describe('when empty response is allowed', function() { beforeEach(function() { extendedRequestOptions.allowEmptyResponse = true; @@ -216,7 +237,7 @@ describe('RequestWrapper', function() { expect(error).to.be.an.instanceOf(EscherRequestError); expect(error.code).to.eql(404); expect(error.message).to.eql('Error in http response (status: 404)'); - expect(error.data).to.eql(JSON.stringify({ replyText: '404 Not Found' })); + expect(error.data).to.eql({ replyText: '404 Not Found' }); } }); }); @@ -340,7 +361,7 @@ describe('RequestWrapper', function() { expect(error).to.be.an.instanceOf(EscherRequestError); expect(error.code).to.eql(404); expect(error.message).to.eql('Error in http response (status: 404)'); - expect(error.data).to.eql(JSON.stringify({ replyText: '404 Not Found' })); + expect(error.data).to.eql({ replyText: '404 Not Found' }); } }); diff --git a/src/wrapper.ts b/src/wrapper.ts index b303e0c..159209c 100644 --- a/src/wrapper.ts +++ b/src/wrapper.ts @@ -109,10 +109,22 @@ export class RequestWrapper { code: error.response.status, reply_text: (error.response?.data || '') })); + let data = ''; + if (error.response != null && + this.isJsonResponse(error.response) && + error.response.data != null && + typeof error.response.data === 'string') { + try { + data = JSON.parse(error.response.data); + } catch (_) { + data = error.response.data; + } + } + throw new EscherRequestError( 'Error in http response (status: ' + error.response.status + ')', error.response.status, - (error.response?.data || '') as string + data ); } else { if (!axios.isCancel(error)) { @@ -142,7 +154,7 @@ export class RequestWrapper { }; } - private isJsonResponse(response: TransformedResponse) { + private isJsonResponse(response: T) { return response.headers['content-type'] && response.headers['content-type'].indexOf('application/json') !== -1; }