UNPKG

hazelcast-client

Version:

Hazelcast - open source In-Memory Data Grid - client for NodeJS

199 lines 8.55 kB
"use strict"; var ClientMessage = require("../ClientMessage"); var Promise = require("bluebird"); var Long = require("long"); var Address = require("../Address"); var ExceptionCodec = require("../codec/ExceptionCodec"); var BitsUtil_1 = require("../BitsUtil"); var LoggingService_1 = require("../logging/LoggingService"); var events_1 = require("events"); var EXCEPTION_MESSAGE_TYPE = 109; var INVOCATION_TIMEOUT = 120000; var INVOCATION_RETRY_DELAY = 1000; var Invocation = (function () { function Invocation(request) { this.deadline = new Date(new Date().getTime() + INVOCATION_TIMEOUT); this.request = request; } Invocation.prototype.hasPartitionId = function () { return this.hasOwnProperty('partitionId') && this.partitionId >= 0; }; return Invocation; }()); exports.Invocation = Invocation; var InvocationService = (function () { function InvocationService(hazelcastClient) { this.correlationCounter = 1; this.eventHandlers = {}; this.pending = {}; this.logger = LoggingService_1.LoggingService.getLoggingService(); this.client = hazelcastClient; this.smartRoutingEnabled = hazelcastClient.getConfig().networkConfig.smartRouting; if (hazelcastClient.getConfig().networkConfig.smartRouting) { this.invoke = this.invokeSmart; } else { this.invoke = this.invokeNonSmart; } } InvocationService.prototype.invokeOnConnection = function (connection, request, handler) { var invocation = new Invocation(request); invocation.connection = connection; if (handler) { invocation.handler = handler; } return this.invoke(invocation); }; InvocationService.prototype.invokeOnPartition = function (request, partitionId) { var invocation = new Invocation(request); invocation.partitionId = partitionId; return this.invoke(invocation); }; InvocationService.prototype.invokeOnTarget = function (request, target) { var invocation = new Invocation(request); invocation.address = target; return this.invoke(invocation); }; InvocationService.prototype.invokeOnRandomTarget = function (request) { return this.invoke(new Invocation(request)); }; InvocationService.prototype.invokeSmart = function (invocation) { if (invocation.hasOwnProperty('connection')) { return this.send(invocation, invocation.connection); } else if (invocation.hasPartitionId()) { var address = this.client.getPartitionService().getAddressForPartition(invocation.partitionId); return this.sendToAddress(invocation, address); } else if (invocation.hasOwnProperty('address')) { return this.sendToAddress(invocation, invocation.address); } else { return this.send(invocation, this.client.getClusterService().getOwnerConnection()); } }; InvocationService.prototype.invokeNonSmart = function (invocation) { if (invocation.hasOwnProperty('connection')) { return this.send(invocation, invocation.connection); } else { return this.send(invocation, this.client.getClusterService().getOwnerConnection()); } }; InvocationService.prototype.sendToAddress = function (invocation, address) { var _this = this; return this.client.getConnectionManager().getOrConnect(address) .then(function (connection) { return _this.send(invocation, connection); }); }; InvocationService.prototype.send = function (invocation, connection) { var correlationId = this.correlationCounter++; var message = invocation.request; message.setCorrelationId(Long.fromNumber(correlationId)); if (invocation.hasPartitionId()) { message.setPartitionId(invocation.partitionId); } else { message.setPartitionId(-1); } invocation.deferred = Promise.defer(); if (invocation.hasOwnProperty('handler')) { this.eventHandlers[correlationId] = invocation; } this.pending[correlationId] = invocation; var logger = this.logger; connection.write(invocation.request.getBuffer(), function (err) { if (err) { logger.warn('InvocationService', 'Error sending message to ' + Address.encodeToString(connection.address) + ' ' + err); invocation.deferred.reject(err); } }); return invocation.deferred.promise; }; InvocationService.prototype.removeEventHandler = function (id) { if (this.eventHandlers.hasOwnProperty('' + id)) { delete this.eventHandlers[id]; } }; InvocationService.prototype.processResponse = function (buffer) { var _this = this; var clientMessage = new ClientMessage(buffer); var correlationId = clientMessage.getCorrelationId().toNumber(); var messageType = clientMessage.getMessageType(); if (clientMessage.hasFlags(BitsUtil_1.BitsUtil.LISTENER_FLAG)) { setImmediate(function () { _this.eventHandlers[correlationId].handler(clientMessage); }); return; } var invocationFinished = true; var pendingInvocation = this.pending[correlationId]; var deferred = pendingInvocation.deferred; if (messageType === EXCEPTION_MESSAGE_TYPE) { var remoteException = ExceptionCodec.decodeResponse(clientMessage); var boundToConnection = pendingInvocation.connection; var deadlineExceeded = new Date().getTime() > pendingInvocation.deadline.getTime(); var shouldRetry = !boundToConnection && !deadlineExceeded && remoteException.isRetryable(); if (shouldRetry) { invocationFinished = false; setTimeout(function () { _this.invoke(pendingInvocation); }, INVOCATION_RETRY_DELAY); } else { this.logger.trace('InvocationService', 'Received exception as response', remoteException); deferred.reject(remoteException); } } else { deferred.resolve(clientMessage); } if (invocationFinished) { delete this.pending[correlationId]; } }; return InvocationService; }()); exports.InvocationService = InvocationService; var ListenerService = (function () { function ListenerService(client) { this.listenerIdToCorrelation = {}; this.client = client; this.internalEventEmitter = new events_1.EventEmitter(); this.internalEventEmitter.setMaxListeners(0); } ListenerService.prototype.registerListener = function (request, handler, decoder, key) { var _this = this; if (key === void 0) { key = undefined; } var deferred = Promise.defer(); var invocation = new Invocation(request); invocation.handler = handler; this.client.getInvocationService().invoke(invocation).then(function (responseMessage) { var correlationId = responseMessage.getCorrelationId(); var response = decoder(responseMessage); _this.listenerIdToCorrelation[response.response] = correlationId; deferred.resolve(response.response); }); return deferred.promise; }; ListenerService.prototype.deregisterListener = function (request, decoder) { var _this = this; var deferred = Promise.defer(); var invocation = new Invocation(request); var listenerIdToCorrelation = this.listenerIdToCorrelation; this.client.getInvocationService().invoke(invocation).then(function (responseMessage) { var correlationId = responseMessage.getCorrelationId().toString(); if (listenerIdToCorrelation.hasOwnProperty(correlationId)) { _this.client.getInvocationService().removeEventHandler(listenerIdToCorrelation[correlationId].low); delete listenerIdToCorrelation[correlationId]; } var response = decoder(responseMessage); deferred.resolve(response.response); }); return deferred.promise; }; return ListenerService; }()); exports.ListenerService = ListenerService; //# sourceMappingURL=InvocationService.js.map