vulcain-corejs
Version:
Vulcain micro-service framework
146 lines (144 loc) • 6.61 kB
JavaScript
;
var __decorate = (this && this.__decorate) || function (decorators, target, key, desc) {
var c = arguments.length, r = c < 3 ? target : desc === null ? desc = Object.getOwnPropertyDescriptor(target, key) : desc, d;
if (typeof Reflect === "object" && typeof Reflect.decorate === "function") r = Reflect.decorate(decorators, target, key, desc);
else for (var i = decorators.length - 1; i >= 0; i--) if (d = decorators[i]) r = (c < 3 ? d(r) : c > 3 ? d(target, key, r) : d(target, key)) || r;
return c > 3 && r && Object.defineProperty(target, key, r), r;
};
var __metadata = (this && this.__metadata) || function (k, v) {
if (typeof Reflect === "object" && typeof Reflect.metadata === "function") return Reflect.metadata(k, v);
};
var __param = (this && this.__param) || function (paramIndex, decorator) {
return function (target, key) { decorator(target, key, paramIndex); }
};
var __awaiter = (this && this.__awaiter) || function (thisArg, _arguments, P, generator) {
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) : new P(function (resolve) { resolve(result.value); }).then(fulfilled, rejected); }
step((generator = generator.apply(thisArg, _arguments)).next());
});
};
const rest = require('unirest');
const annotations_1 = require("./../../di/annotations");
const metrics_1 = require("../../metrics/metrics");
const httpCommandError_1 = require("../../errors/httpCommandError");
const system_1 = require("../../configurations/globals/system");
let AbstractHttpCommand = class AbstractHttpCommand {
constructor(container) {
this.metrics = container.get(annotations_1.DefaultServiceNames.Metrics);
this.initializeMetricsInfo(container);
}
get container() {
return this.requestContext.container;
}
initializeMetricsInfo(container) {
let dep = this.constructor["$dependency:external"];
if (dep) {
this.setMetricsTags(container, dep.uri);
}
}
/**
* Set metric tags for this command
*
* @protected
* @param {any} tags
*
* @memberOf AbstractHttpCommand
*/
setMetricsTags(container, uri) {
if (!uri)
throw new Error("Metrics tags must have an uri property.");
let exists = system_1.System.manifest.dependencies.externals.find(ex => ex.uri === uri);
if (!exists) {
system_1.System.manifest.dependencies.externals.push({ uri });
}
this.customTags = this.metrics.encodeTags("uri=" + uri);
let logger = container.get(annotations_1.DefaultServiceNames.Logger);
logger.logAction(this.requestContext, "BC", "Http", uri);
}
onCommandCompleted(duration, success) {
this.metrics.timing(AbstractHttpCommand.METRICS_NAME + metrics_1.MetricsConstant.duration, duration, this.customTags);
if (!success)
this.metrics.increment(AbstractHttpCommand.METRICS_NAME + metrics_1.MetricsConstant.failure, this.customTags);
let logger = this.container.get(annotations_1.DefaultServiceNames.Logger);
logger.logAction(this.requestContext, "EC");
}
runAsync(...args) {
return this.execAsync(...args);
}
execAsync(verb, url, data) {
return __awaiter(this, void 0, void 0, function* () {
this.setMetricsTags(this.container, url);
if (system_1.System.hasMocks) {
let result = system_1.System.mocks.applyMockHttp(url, verb);
if (result !== undefined) {
return result;
}
}
let method = this[verb + "Async"];
if (!method)
throw new Error(`${verb} is not implemented in AbstractHttpCommand. Use a custom command for this verb.`);
return yield method.apply(this, [url, data]);
});
}
postAsync(url, data) {
return this.sendRequestAsync('post', url, req => req.json(data));
}
getAsync(url) {
return this.sendRequestAsync('get', url);
}
deleteAsync(url) {
return this.sendRequestAsync('delete', url);
}
putAsync(url, data) {
return this.sendRequestAsync('put', url, req => req.json(data));
}
/**
* Send a http request
*
* @protected
* @param {string} http verb to use
* @param {string} url
* @param {(req:types.IHttpRequest) => void} [prepareRequest] Callback to configure request before sending
* @returns request response
*/
sendRequestAsync(verb, url, prepareRequest) {
let request = rest[verb](url);
prepareRequest && prepareRequest(request);
system_1.System.log.info(this.requestContext, `Calling (${verb}) ${system_1.System.removePasswordFromUrl(url)}`);
return new Promise((resolve, reject) => {
request.end((response) => {
if (response.status >= 400) {
let msg = `Http request ${verb} ${url} failed with status code ${response.status}`;
system_1.System.log.info(this.requestContext, msg);
reject(new httpCommandError_1.HttpCommandError(msg, response));
return;
}
if (response.error) {
let msg = `Error on http request ${verb} ${url} - ${response.error}`;
reject(this.handleError(msg, response.error));
return;
}
system_1.System.log.info(this.requestContext, `Http request ${verb} ${url} completed succesfully (code:${response.status}).`);
resolve(response);
});
});
}
handleError(msg, err) {
system_1.System.log.error(this.requestContext, err, msg);
if (err && !(err instanceof Error)) {
let tmp = err;
err = new Error(msg);
err.error = tmp;
}
return new httpCommandError_1.HttpCommandError(msg, err, 500);
}
};
AbstractHttpCommand.METRICS_NAME = "external_call";
AbstractHttpCommand = __decorate([
__param(0, annotations_1.Inject(annotations_1.DefaultServiceNames.Container)),
__metadata("design:paramtypes", [Object])
], AbstractHttpCommand);
exports.AbstractHttpCommand = AbstractHttpCommand;
//# sourceMappingURL=abstractHttpCommand.js.map