@ablestack/rdo-apollo-mobx-connector
Version:
A library to connect Apollo GraphQL Query Results to MobX, leveraging Reactive Domain Objects
118 lines • 4.97 kB
JavaScript
"use strict";
Object.defineProperty(exports, "__esModule", { value: true });
exports.QueryWatcher = void 0;
const tslib_1 = require("tslib");
const uuid_1 = tslib_1.__importDefault(require("uuid"));
const logger_1 = require("@ablestack/rdo/infrastructure/logger");
const deferred_promise_ts_1 = require("@ablestack/deferred-promise-ts");
const logger = logger_1.Logger.make('ViewModelSyncUtils');
class QueryWatcher {
constructor({ name, makeObservableQuery, onAfterInitialized, onAfterStart: onStart, onDataChange, onAfterStop: onStop, }) {
this._active = false;
this._uuid = uuid_1.default.v4();
this._deferredPromiseQueue = new Array();
this._name = name;
this._makeObservableQuery = makeObservableQuery;
this._onAfterInitialized = onAfterInitialized;
this._onAfterStart = onStart;
this._handleDataChange = onDataChange;
this._onAfterStop = onStop;
}
get active() {
return this._active;
}
//
async initialize(apolloClient) {
if (!this._watchedQuery) {
this._watchedQuery = await this._makeObservableQuery(apolloClient);
logger.trace(`${this._name} - watchedQuery initialized`, this._watchedQuery);
}
if (this._onAfterInitialized) {
await this._onAfterInitialized(apolloClient);
}
}
/**
*
*
* @param {ApolloClient<NormalizedCacheObject>} apolloClient
* @param {boolean} [force=false] the force parameter will override any existing watch, and trigger a refetch of data even if data already available
* @returns
* @memberof QueryWatcher
*/
start(apolloClient, force) {
if (this.active)
return;
this.initiateWatch({ apolloClient, runOnce: false, force });
logger.trace(`${this._name} - Started`);
if (this._onAfterStart)
this._onAfterStart(apolloClient);
}
//
runOnce(apolloClient) {
if (this.active)
return;
this.initiateWatch({ apolloClient, runOnce: true, force: true });
logger.trace(`${this._name} - RunOnce`);
if (this._onAfterStart)
this._onAfterStart(apolloClient);
}
//
stop(apolloClient) {
var _a;
if (this._active) {
(_a = this._watchedQuerySubscription) === null || _a === void 0 ? void 0 : _a.unsubscribe();
this._active = false;
// Reject any queued promises
if (this._deferredPromiseQueue.length > 0) {
//
this._deferredPromiseQueue.splice(0, this._deferredPromiseQueue.length).forEach((item) => item.reject('QueryWatcher stopped before DeferredPromise containing results resolved'));
}
logger.trace(`${this._name} - Stopped`);
if (this._onAfterStop)
this._onAfterStop(apolloClient);
}
}
// The force parameter will trigger a refetch of data even if already available
initiateWatch({ apolloClient, runOnce, force }) {
if (!this._watchedQuery) {
logger.error(`QueryWatcher must be initialized before use (${this._name})`, this._watchedQuery);
return;
}
logger.info(`${this._name} - Starting`);
if (!force && this._active)
throw new Error(`queryWatch already active. To override an existing queryWatch session, set the 'force' parameter of the Start method to 'true'`);
if (force)
this._watchedQuery.resetLastResults();
this._watchedQuerySubscription = this._watchedQuery.subscribe((next) => {
logger.trace(`${this._name} - watchedQuerySubscription - Result`, next);
if (next.data) {
this.onDataChange(next.data);
if (runOnce)
this.stop(apolloClient);
}
}, (error) => {
logger.error(`${this._name} - watchedQuerySubscription - ERROR`, error);
this.stop(apolloClient);
}, () => {
logger.info(`${this._name} - watchedQuerySubscription - Completed`);
this.stop(apolloClient);
});
this._active = true;
}
async getNextResultAsync() {
const deferredPromise = new deferred_promise_ts_1.DeferredPromise();
this._deferredPromiseQueue.push(deferredPromise);
return deferredPromise;
}
onDataChange(queryResult) {
// Call data change handlers
this._handleDataChange(queryResult);
// Resolve any queued promises
if (this._deferredPromiseQueue.length > 0) {
//
this._deferredPromiseQueue.splice(0, this._deferredPromiseQueue.length).forEach((item) => item.resolve(queryResult));
}
}
}
exports.QueryWatcher = QueryWatcher;
//# sourceMappingURL=queryWatcher.js.map