diff --git a/CHANGELOG.md b/CHANGELOG.md index 5c82c33..46be12f 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -1,5 +1,9 @@ # Change Log +## [4.17.0](https://github.com/plivo/plivo-node/releases/tag/v4.17.0)(2021-05-04) +- Add Exception Support +- Updated README + ## [4.16.0](https://github.com/plivo/plivo-node/releases/tag/v4.16.0)(2021-04-19) - Added SDK support for Voice MultiPartyCall APIs and XML diff --git a/README.md b/README.md index 9befb13..2c454a1 100644 --- a/README.md +++ b/README.md @@ -127,4 +127,4 @@ console.log('Phlo run result', result); More examples are available [here](https://github.com/plivo/plivo-examples-node). Also refer to the [guides for configuring the Express server to run various scenarios](https://www.plivo.com/docs/sms/quickstart/node-expressjs/) & use it to test out your integration in under 5 minutes. ## Reporting issues -Report any feedback or problems with this version by [opening an issue on Github](https://github.com/plivo/plivo-node/issues). +Report any feedback or problems with this version by [opening an issue on Github](https://github.com/plivo/plivo-node/issues). \ No newline at end of file diff --git a/lib/rest/axios.js b/lib/rest/axios.js index d323f07..61f8cde 100644 --- a/lib/rest/axios.js +++ b/lib/rest/axios.js @@ -1,8 +1,11 @@ -import axios from 'axios'; -import queryString from 'querystring'; import * as Exceptions from '../utils/exceptions'; import * as _ from "lodash"; +import axios from 'axios'; +import queryString from 'querystring'; + +var HttpsProxyAgent = require('https-proxy-agent'); + export function Axios(config) { let auth = 'Basic ' + new Buffer(config.authId + ':' + config.authToken) .toString('base64'); @@ -84,7 +87,25 @@ export function Axios(config) { }); }) .catch(function (error) { - reject(error.stack+ "\r\n" + JSON.stringify(error.response.data)); + const exceptionClass = { + 400: Exceptions.InvalidRequestError, + 401: Exceptions.AuthenticationError, + 404: Exceptions.ResourceNotFoundError, + 405: Exceptions.InvalidRequestError, + 500: Exceptions.ServerError, + } [error.response.status] || Error; + if (!_.inRange(error.response.status, 200, 300)) { + let body = error.response.data; + if (typeof body === 'object') { + reject(new exceptionClass(error)); + } else { + if (error.response.status >= 500) { + reject(new Exceptions.ServerError(error)); + } + reject(new exceptionClass(error)); + } + } + reject(error.stack + '\n' + JSON.stringify(error.response.data)); }); }) } @@ -137,7 +158,7 @@ export function Axios(config) { } if (typeof config.proxy !== 'undefined') { - options.proxy = config.proxy; + options.httpsAgent = new HttpsProxyAgent(config.proxy); } if (typeof config.timeout !== 'undefined') { @@ -172,7 +193,25 @@ export function Axios(config) { }); }) .catch(function (error) { - reject(error.stack+ "\r\n" + JSON.stringify(error.response.data)); + const exceptionClass = { + 400: Exceptions.InvalidRequestError, + 401: Exceptions.AuthenticationError, + 404: Exceptions.ResourceNotFoundError, + 405: Exceptions.InvalidRequestError, + 500: Exceptions.ServerError, + } [error.response.status] || Error; + if (!_.inRange(error.response.status, 200, 300)) { + let body = error.response.data; + if (typeof body === 'object') { + reject(new exceptionClass(error)); + } else { + if (error.response.status >= 500) { + reject(new Exceptions.ServerError(error)); + } + reject(new exceptionClass(error)); + } + } + reject(error.stack + '\n' + JSON.stringify(error.response.data)); }) } else { @@ -207,6 +246,24 @@ export function Axios(config) { } }) .catch(function (error) { + const exceptionClass = { + 400: Exceptions.InvalidRequestError, + 401: Exceptions.AuthenticationError, + 404: Exceptions.ResourceNotFoundError, + 405: Exceptions.InvalidRequestError, + 500: Exceptions.ServerError, + } [error.response.status] || Error; + if (!_.inRange(error.response.status, 200, 300)) { + let body = error.response.data; + if (typeof body === 'object') { + reject(new exceptionClass(error)); + } else { + if (error.response.status >= 500) { + reject(new Exceptions.ServerError(error)); + } + reject(new exceptionClass(error)); + } + } reject(error.stack + '\n' + JSON.stringify(error.response.data)); }) } diff --git a/lib/utils/exceptions.js b/lib/utils/exceptions.js index 04805f2..9d72ae0 100644 --- a/lib/utils/exceptions.js +++ b/lib/utils/exceptions.js @@ -1,4 +1,4 @@ -export class PlivoRestError extends Error { } +var PlivoRestError = require('./restException'); export class ResourceNotFoundError extends PlivoRestError { } export class ServerError extends PlivoRestError { } export class InvalidRequestError extends PlivoRestError { } diff --git a/lib/utils/restException.js b/lib/utils/restException.js new file mode 100644 index 0000000..d41e200 --- /dev/null +++ b/lib/utils/restException.js @@ -0,0 +1,20 @@ + +class PlivoRestError extends Error { + constructor(response) { + response = response.response + var body; + super('[HTTP ' + response.status + '] Failed to execute request'); + try { + body = typeof response.data === 'string' ? JSON.parse(response.data) : response.data; + } catch (err) { + body = {"error": response.data, "api_id": ''} + } + this.status = response.status; + this.statusText = response.statusText + this.message = body.error; + this.apiID = body.api_id; + this.moreInfo = response.config.data + } +} + +module.exports = PlivoRestError; diff --git a/package.json b/package.json index 7df55cd..683199f 100644 --- a/package.json +++ b/package.json @@ -1,6 +1,6 @@ { "name": "plivo", - "version": "4.16.0", + "version": "4.17.0", "description": "A Node.js SDK to make voice calls and send SMS using Plivo and to generate Plivo XML", "homepage": "https://github.com/plivo/plivo-node", "files": [ @@ -59,8 +59,9 @@ }, "dependencies": { "@types/node": "^14.14.14", - "axios": "^0.19.2", + "axios": "^0.21.1", "base-64": "^0.1.0", + "https-proxy-agent": "^5.0.0", "build-url": "^1.0.10", "form-data": "^4.0.0", "jsonwebtoken": "^8.5.1",