UNPKG

@stackbit/utils

Version:
65 lines 2.37 kB
"use strict"; var __importDefault = (this && this.__importDefault) || function (mod) { return (mod && mod.__esModule) ? mod : { "default": mod }; }; Object.defineProperty(exports, "__esModule", { value: true }); exports.Worker = void 0; const lodash_1 = __importDefault(require("lodash")); const promise_utils_1 = require("./promise-utils"); class Worker { constructor() { this.promise = Promise.resolve(); this.enqueued = []; } schedule(jobFn) { return new Promise((resolve, reject) => { this.promise = this.promise.finally(() => { const res = jobFn(); if (res && typeof lodash_1.default.get(res, 'then') === 'function') { return res.then(resolve).catch(reject); } else { resolve(res); } }); }); } /** * Run one after another 2 calls of same jobFn, 3rd and next calls will be waiting for finishing 2nd and * respond all together * In case there are another jobFn called on the same worker - 2nd round of calls would be postponed to process next call * to prevent dead lock * @see https://user-images.githubusercontent.com/97896/90123842-1fea2f80-dd68-11ea-8462-d4f1cdc1749b.png * @param {String} jobId * @param {Function} jobFn * @returns {Promise} */ enqueueOnce(jobId, jobFn) { let enqueued = this.enqueued.find((obj) => obj.jobId === jobId); if (enqueued) { if (!enqueued.nextJobFn) { enqueued.nextJobFn = jobFn; } return enqueued.deferred.promise; } enqueued = { jobId, jobFn, deferred: (0, promise_utils_1.deferredPromise)(), nextJobFn: null }; this.enqueued.push(enqueued); return this.schedule(jobFn).finally(() => { if (!enqueued) { return; } const index = this.enqueued.indexOf(enqueued); this.enqueued.splice(index, 1); if (enqueued.nextJobFn) { this.enqueueOnce(enqueued.jobId, enqueued.nextJobFn).then(enqueued.deferred.resolve).catch(enqueued.deferred.reject); } }); } } exports.Worker = Worker; //# sourceMappingURL=worker.js.map