UNPKG

expresscheckout-nodejs

Version:

Juspay's official expresscheckout-nodejs sdk

370 lines 19.7 kB
var __assign = (this && this.__assign) || function () { __assign = Object.assign || function(t) { for (var s, i = 1, n = arguments.length; i < n; i++) { s = arguments[i]; for (var p in s) if (Object.prototype.hasOwnProperty.call(s, p)) t[p] = s[p]; } return t; }; return __assign.apply(this, arguments); }; var __awaiter = (this && this.__awaiter) || function (thisArg, _arguments, P, generator) { function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); } return new (P || (P = Promise))(function (resolve, reject) { function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } } function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } } function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); } step((generator = generator.apply(thisArg, _arguments || [])).next()); }); }; var __generator = (this && this.__generator) || function (thisArg, body) { var _ = { label: 0, sent: function() { if (t[0] & 1) throw t[1]; return t[1]; }, trys: [], ops: [] }, f, y, t, g; return g = { next: verb(0), "throw": verb(1), "return": verb(2) }, typeof Symbol === "function" && (g[Symbol.iterator] = function() { return this; }), g; function verb(n) { return function (v) { return step([n, v]); }; } function step(op) { if (f) throw new TypeError("Generator is already executing."); while (g && (g = 0, op[0] && (_ = 0)), _) try { if (f = 1, y && (t = op[0] & 2 ? y["return"] : op[0] ? y["throw"] || ((t = y["return"]) && t.call(y), 0) : y.next) && !(t = t.call(y, op[1])).done) return t; if (y = 0, t) op = [op[0] & 2, t.value]; switch (op[0]) { case 0: case 1: t = op; break; case 4: _.label++; return { value: op[1], done: false }; case 5: _.label++; y = op[1]; op = [0]; continue; case 7: op = _.ops.pop(); _.trys.pop(); continue; default: if (!(t = _.trys, t = t.length > 0 && t[t.length - 1]) && (op[0] === 6 || op[0] === 2)) { _ = 0; continue; } if (op[0] === 3 && (!t || (op[1] > t[0] && op[1] < t[3]))) { _.label = op[1]; break; } if (op[0] === 6 && _.label < t[1]) { _.label = t[1]; t = op; break; } if (t && _.label < t[2]) { _.label = t[2]; _.ops.push(op); break; } if (t[2]) _.ops.pop(); _.trys.pop(); continue; } op = body.call(thisArg, _); } catch (e) { op = [6, e]; y = 0; } finally { f = t = 0; } if (op[0] & 5) throw op[1]; return { value: op[0] ? op[1] : void 0, done: true }; } }; /* eslint-disable @typescript-eslint/no-explicit-any */ import * as http from 'http'; import * as https from 'https'; import { URL } from 'url'; import Juspay from './Juspay.js'; import { base64Encode, prepareData, prepareQueryParams } from './utils.js'; import { APIError, AuthenticationError, AuthorizationError, InternalServerError, InvalidRequestError, JuspayError, TimeoutError, } from './JuspayError.js'; import security from './security/index.js'; import { DefaultJuspayLogger } from './JuspayLogger.js'; var JuspayResource = /** @class */ (function () { function JuspayResource(juspayEnv) { this.logger = DefaultJuspayLogger.getLoggerInstance(JuspayResource.name); this.juspayEnvironment = juspayEnv; } JuspayResource.prototype.makeServiceCall = function (_a) { var _this = this; var method = _a.method, _b = _a.path, path = _b === void 0 ? '/' : _b, _c = _a.headers, headers = _c === void 0 ? {} : _c, body = _a.body, timeout = _a.timeout, query = _a.query, juspayOverrideConfig = _a.juspayOverrideConfig, _d = _a.auth, auth = _d === void 0 ? ['BASIC'] : _d, _e = _a.opts, opts = _e === void 0 ? { authPriority: 'default' } : _e; return new Promise(function (resolve, reject) { return __awaiter(_this, void 0, void 0, function () { var juspayEnvironment_1, authMethod_1, apiKey, merchantId, jweAuthConfig, dataToEncrypt, data_1, pathWithQueryParams, fullPath, isInsecureConnection_1, agent, httpOptions, req_1; var _this = this; return __generator(this, function (_a) { try { juspayEnvironment_1 = this.juspayEnvironment.override(juspayOverrideConfig); authMethod_1 = this.authDecider(juspayEnvironment_1, auth, opts); headers = __assign(__assign({ 'Content-Type': 'application/x-www-form-urlencoded', 'User-Agent': "NODEJS_SDK/".concat(Juspay.pkg.version), version: juspayEnvironment_1.getVersion(), 'x-merchantid': juspayEnvironment_1.getMerchantId() }, headers), juspayEnvironment_1.getHeaders()); switch (authMethod_1) { case 'BASIC': apiKey = juspayEnvironment_1.getApiKey(), merchantId = juspayEnvironment_1.getMerchantId(); if (apiKey == undefined || merchantId == undefined) { throw new TypeError("Using BASIC auth, please set merchant id and api key to use this resource ".concat(path, ".")); } headers = __assign(__assign({}, headers), { Authorization: 'Basic ' + base64Encode(apiKey) }); break; case 'JWE': jweAuthConfig = juspayEnvironment_1.getJweEncryption(); if (jweAuthConfig == undefined) { throw new TypeError('Using JWE auth, please set jweAuth field in config'); } headers = __assign(__assign({}, headers), { 'Content-Type': 'application/json' }); if (opts.jwePath == undefined) { path = "/v4".concat(path); } else { path = opts.jwePath; } dataToEncrypt = void 0; if (method == 'GET') { method = 'POST'; dataToEncrypt = JSON.stringify(query); } else { dataToEncrypt = JSON.stringify(body); } body = security.JWT.jwtEncrypt(dataToEncrypt, jweAuthConfig.keyId, jweAuthConfig.publicKey, jweAuthConfig.privateKey); break; case 'SIGNATURE': default: throw new TypeError('Auth method not implemented'); } data_1 = ''; if (method != 'GET') { if (headers['Content-Type'] == 'application/x-www-form-urlencoded') { data_1 = prepareData(body); } else { data_1 = JSON.stringify(body); } } this.logger.info({ value: body, message: 'Request parameters' }); pathWithQueryParams = path; if (authMethod_1 != 'JWE') { pathWithQueryParams = path + prepareQueryParams(query); } fullPath = new URL(pathWithQueryParams, juspayEnvironment_1.getBaseUrl()), isInsecureConnection_1 = fullPath.protocol === 'http'; agent = opts.agent; if (!agent) { agent = isInsecureConnection_1 ? new http.Agent({ keepAlive: true }) : new https.Agent({ keepAlive: true }); } this.logger.info({ message: 'Executing request', value: fullPath.pathname + fullPath.search }); httpOptions = { host: fullPath.host, port: fullPath.port, path: fullPath.pathname + fullPath.search, method: method, agent: agent, // eslint-disable-next-line @typescript-eslint/ban-ts-comment // @ts-ignore headers: headers }; req_1 = (isInsecureConnection_1 ? http : https).request(httpOptions); req_1.setTimeout(timeout || juspayEnvironment_1.getTimeout(), function () { req_1.destroy(new TimeoutError('Socket Timeout during request execution')); }); req_1.on('response', function (res) { return __awaiter(_this, void 0, void 0, function () { var httpResponse, _a, error_1; return __generator(this, function (_b) { switch (_b.label) { case 0: this.logger.info({ message: 'Received HTTP Response Code', value: res.statusCode }); httpResponse = new HttpResponseHandler(res, authMethod_1, juspayEnvironment_1.getJweEncryption()); _b.label = 1; case 1: _b.trys.push([1, 3, , 4]); _a = resolve; return [4 /*yield*/, httpResponse.parseResponse()]; case 2: _a.apply(void 0, [_b.sent()]); return [3 /*break*/, 4]; case 3: error_1 = _b.sent(); this.logger.error(error_1); reject(error_1); return [3 /*break*/, 4]; case 4: return [2 /*return*/]; } }); }); }); req_1.on('error', function (error) { _this.logger.error({ message: 'Please check your internet connection/Failed to establish connection', value: error }); reject(error); }); req_1.once('socket', function (socket) { if (socket.connecting) { socket.once(isInsecureConnection_1 ? 'connect' : 'secureConnect', function () { req_1.write(data_1); req_1.end(); }); } else { req_1.write(data_1); req_1.end(); } }); } catch (error) { this.logger.error(error); return [2 /*return*/, reject(error)]; } return [2 /*return*/]; }); }); }); }; JuspayResource.prototype.authDecider = function (juspayEnvironment, auth, opts) { var defaultPriority = [ 'JWE', 'SIGNATURE', 'BASIC', ]; var priority = []; if (opts.authPriority == 'default' || opts.authPriority == undefined) { for (var i = 0; i < defaultPriority.length; i++) { var authMethod = defaultPriority[i]; if (auth.includes(authMethod)) { priority.push(authMethod); } } } else { priority = auth; } for (var i = 0; i < priority.length; i++) { var authMethod = priority[i]; switch (authMethod) { case 'BASIC': if (juspayEnvironment.getApiKey() && juspayEnvironment.getMerchantId()) { return 'BASIC'; } break; case 'JWE': if (juspayEnvironment.getJweEncryption()) { return 'JWE'; } break; case 'SIGNATURE': default: throw new TypeError(authMethod + ' auth is not implemented'); } } if (juspayEnvironment.getApiKey() && juspayEnvironment.getMerchantId() && opts.authPriority != 'ordered') { return 'BASIC'; } if (priority.includes('BASIC') == false) { priority.push('BASIC'); } var errorMessage = "No authentication config found in Juspay instance. Please setup the config to support this auth ".concat(priority, ".\n For JWE encryption. Setup using new Juspay(jweAuth: {keyId:string, publicKey:string, privateKey: string}, merchantId:string). You can get these configs from dashboard under security>JWT section.\n For BASIC authentication. Setup using new Juspay({apiKey:string, merchantId:string}), you can get apiKey from dashboard under security?API KEYS.\n Please ensure merchantId has been set.\n "); throw new TypeError(errorMessage); }; return JuspayResource; }()); var HttpResponseHandler = /** @class */ (function () { function HttpResponseHandler(res, authMethod, jweAuthConfig) { this.logger = DefaultJuspayLogger.getLoggerInstance(HttpResponseHandler.name); // eslint-disable-next-line @typescript-eslint/ban-ts-comment // @ts-ignore this.__status_code = res.statusCode; // eslint-disable-next-line @typescript-eslint/ban-ts-comment // @ts-ignore this.__headers = res.headers || {}; this.__res = res; this.__jwe_auth_config = jweAuthConfig; this.__auth_method = authMethod; } HttpResponseHandler.prototype.getRawResponse = function () { return this.__res; }; HttpResponseHandler.prototype.getStatusCode = function () { return this.__status_code; }; HttpResponseHandler.prototype.getHeaders = function () { return this.__headers; }; HttpResponseHandler.prototype.toStream = function (streamCompleteCallback) { this.__res.once('end', function () { return streamCompleteCallback(); }); return this.__res; }; HttpResponseHandler.prototype.parseResponse = function () { var _this = this; return new Promise(function (resolve, reject) { if (_this.__response != undefined) { return resolve(_this.__response); } var response = ''; _this.__res.setEncoding('utf8'); _this.__res.on('data', function (chunk) { response += chunk; }); _this.__res.once('end', function () { return __awaiter(_this, void 0, void 0, function () { var http, resJson, finalResponse, decryptedResponse, statusCode; return __generator(this, function (_a) { this.__response = response; http = { headers: this.getHeaders(), statusCode: this.getStatusCode(), url: this.__res.url, method: this.__res.method, httpVersion: this.__res.httpVersion, httpVersionMajor: this.__res.httpVersionMajor, httpVersionMinor: this.__res.httpVersionMinor, headersDistinct: this.__res.headersDistinct, rawHeaders: this.__res.rawHeaders, statusMessage: this.__res.statusMessage }; try { resJson = JSON.parse(response); this.__response = resJson; this.logger.info({ message: 'Received response', value: resJson }); } catch (e) { this.logger.info({ message: 'Received response', value: response }); reject(new InternalServerError(this.__response)); } finalResponse = __assign(__assign({}, resJson), { http: http }); try { if (this.__status_code >= 200 && this.__status_code < 300) { switch (this.__auth_method) { case 'JWE': decryptedResponse = this.jweDecryptRequest(resJson); finalResponse = __assign(__assign({}, decryptedResponse), { http: http }); break; case 'BASIC': case 'SIGNATURE': default: finalResponse = __assign(__assign({}, resJson), { http: http }); } return [2 /*return*/, resolve(finalResponse)]; } else { statusCode = this.__res.statusCode; if (statusCode == 400 || statusCode == 404) return [2 /*return*/, reject(new InvalidRequestError(this.__response))]; else if (statusCode == 401) return [2 /*return*/, reject(new AuthenticationError(this.__response))]; else if (statusCode == 403) return [2 /*return*/, reject(new AuthorizationError(this.__response))]; else return [2 /*return*/, reject(new APIError(this.__response))]; } } catch (err) { reject(new JuspayError(err)); } return [2 /*return*/]; }); }); }); }); }; HttpResponseHandler.prototype.jweDecryptRequest = function (body) { var jweAuthConfig = this.__jwe_auth_config; if (jweAuthConfig == undefined) { throw new TypeError('Please setup jwe encryption keys to use jwe + jws auth.'); } var res = security.JWT.jwtDecrypt(body, jweAuthConfig.keyId, jweAuthConfig.publicKey, jweAuthConfig.privateKey); return JSON.parse(res); }; return HttpResponseHandler; }()); export default JuspayResource; //# sourceMappingURL=JuspayResource.js.map