"use strict";
var websocket = require('websocket');
var W3CWebSocket = websocket['w3cwebsocket'];
var messageTypes_1 = require('./messageTypes');
var lodash_1 = require('lodash');
var DEFAULT_SUBSCRIPTION_TIMEOUT = 5000;
var Client = (function () {
function Client(url, options) {
var _this = this;
this.client = new W3CWebSocket(url, 'graphql-subscriptions');
this.subscriptionHandlers = {};
this.maxId = 0;
this.subscriptionTimeout = (options && options.timeout) || DEFAULT_SUBSCRIPTION_TIMEOUT;
this.waitingSubscriptions = {};
this.client.onmessage = function (message) {
var parsedMessage;
try {
parsedMessage = JSON.parse(message.data);
}
catch (e) {
throw new Error('Message must be JSON-parseable.');
}
var subId = parsedMessage.id;
if (!_this.subscriptionHandlers[subId]) {
_this.unsubscribe(subId);
return;
}
switch (parsedMessage.type) {
case messageTypes_1.SUBSCRIPTION_SUCCESS:
delete _this.waitingSubscriptions[subId];
break;
case messageTypes_1.SUBSCRIPTION_FAIL:
if (_this.subscriptionHandlers[subId]) {
_this.subscriptionHandlers[subId](parsedMessage.errors, null);
}
delete _this.subscriptionHandlers[subId];
delete _this.waitingSubscriptions[subId];
break;
case messageTypes_1.SUBSCRIPTION_DATA:
if (parsedMessage.payload.data && !parsedMessage.payload.errors) {
_this.subscriptionHandlers[subId](null, parsedMessage.payload.data);
}
else {
_this.subscriptionHandlers[subId](parsedMessage.payload.errors, null);
}
break;
default:
throw new Error('Invalid message type - must be of type `subscription_start` or `subscription_data`.');
}
};
}
Client.prototype.subscribe = function (options, handler) {
var _this = this;
var query = options.query, variables = options.variables, operationName = options.operationName;
if (!query || !variables || !operationName) {
I throw new Error('Must provide `query`, `variables`, and `operationName` to subscribe.');
}
if (!handler) {
I throw new Error('Must provide `handler` to subscribe.');
}
if (!lodash_1.isString(query) || !lodash_1.isString(operationName) || !lodash_1.isObject(variables)) {
I throw new Error('Incorrect option types to subscribe. `subscription` must be a string,' +
'`operationName` must be a string, and `variables` must be an object.');
}
switch (this.client.readyState) {
case this.client.OPEN:
var subId_1 = this.generateSubscriptionId();
var message = Object.assign(options, { type: messageTypes_1.SUBSCRIPTION_START, id: subId_1 });
this.sendMessage(message);
this.subscriptionHandlers[subId_1] = handler;
this.waitingSubscriptions[subId_1] = true;
setTimeout(function () {
Eif (_this.waitingSubscriptions[subId_1]) {
handler(new Error('Subscription timed out - no response from server'));
_this.unsubscribe(subId_1);
}
}, this.subscriptionTimeout);
return subId_1;
case this.client.CONNECTING:
throw new Error('Client is still connecting to websocket.');
case this.client.CLOSING:
throw new Error('Client websocket connection is closing.');
case this.client.CLOSED:
throw new Error('Client is not connected to a websocket.');
default:
throw new Error('Client is not connected to a websocket.');
}
};
Client.prototype.unsubscribe = function (id) {
delete this.subscriptionHandlers[id];
Eif (this.client.readyState === this.client.OPEN) {
var message = { id: id, type: messageTypes_1.SUBSCRIPTION_END };
this.sendMessage(message);
}
};
Client.prototype.unsubscribeAll = function () {
var _this = this;
Object.keys(this.subscriptionHandlers).forEach(function (subId) {
_this.unsubscribe(subId);
});
};
Client.prototype.sendMessage = function (message) {
Eif (this.client.readyState === this.client.OPEN) {
this.client.send(JSON.stringify(message));
}
else {
throw new Error('Cannot send message. WebSocket connection is not open');
}
};
Client.prototype.generateSubscriptionId = function () {
var id = this.maxId;
this.maxId += 1;
return id;
};
return Client;
}());
Object.defineProperty(exports, "__esModule", { value: true });
exports.default = Client;
;
//# sourceMappingURL=client.js.map |