hydrate-mongodb
Version:
An Object Document Mapper (ODM) for MongoDB.
123 lines (122 loc) • 4.08 kB
JavaScript
"use strict";
var __extends = (this && this.__extends) || (function () {
var extendStatics = Object.setPrototypeOf ||
({ __proto__: [] } instanceof Array && function (d, b) { d.__proto__ = b; }) ||
function (d, b) { for (var p in b) if (b.hasOwnProperty(p)) d[p] = b[p]; };
return function (d, b) {
extendStatics(d, b);
function __() { this.constructor = d; }
d.prototype = b === null ? Object.create(b) : (__.prototype = b.prototype, new __());
};
})();
Object.defineProperty(exports, "__esModule", { value: true });
var events_1 = require("events");
var persistenceError_1 = require("./persistenceError");
var TaskQueue = (function (_super) {
__extends(TaskQueue, _super);
function TaskQueue(execute) {
var _this = _super.call(this) || this;
_this._activeCounts = {};
_this._active = 0;
_this._execute = execute;
return _this;
}
TaskQueue.prototype.add = function (operation, wait, arg, callback) {
var _this = this;
var err;
if (this._closed) {
err = new persistenceError_1.PersistenceError("Session is closed.");
}
if (this._invalid) {
err = new persistenceError_1.PersistenceError("Session is invalid. An error occurred during a previous action.");
}
if (err) {
callback ? callback(err) : this._unhandledError(err);
return;
}
var task = {
operation: operation,
wait: wait,
arg: arg,
callback: callback,
finished: false
};
if (this._activeCounts[operation] === undefined) {
this._activeCounts[operation] = 0;
}
if (this._head) {
this._tail = this._tail.next = task;
}
else {
this._head = this._tail = task;
process.nextTick(function () { return _this._process(); });
}
};
Object.defineProperty(TaskQueue.prototype, "invalid", {
get: function () {
return this._invalid;
},
enumerable: true,
configurable: true
});
TaskQueue.prototype.close = function () {
this._closed = true;
this._clear();
};
TaskQueue.prototype._process = function () {
var task = this._head;
while (task && !(task.wait & this._active)) {
this._head = this._head.next;
if (!this._activeCounts[task.operation]++) {
this._active |= task.operation;
}
this._execute(task.operation, task.arg, this._finished(task));
task = this._head;
}
};
TaskQueue.prototype._finished = function (task) {
var _this = this;
return function (err, result) {
if (task.finished) {
throw new persistenceError_1.PersistenceError("Callback for task can only be called once.");
}
task.finished = true;
if (!(--_this._activeCounts[task.operation])) {
_this._active &= ~task.operation;
}
if (err) {
_this._invalid = true;
}
if (task.callback) {
task.callback(err, result);
}
if (err) {
if (!task.callback) {
_this._unhandledError(err);
}
_this._clear();
return;
}
if (_this._head) {
_this._process();
}
};
};
TaskQueue.prototype._unhandledError = function (err) {
var task = this._head;
while (task && !task.callback) {
task = task.next;
}
if (task && task.callback) {
task.callback(err);
}
else {
this.emit('error', err);
}
};
TaskQueue.prototype._clear = function () {
this._head = this._tail = null;
};
return TaskQueue;
}(events_1.EventEmitter));
exports.TaskQueue = TaskQueue;