/*jslint nomen: true, maxlen: 200*/ /*global RSVP, console*/ (function (jIO) { "use strict"; /** * The jIO CacheStorage extension * * @class CacheStorage * @constructor */ // XXX Delete entry when put post delete function enqueueDefer(storage, callback) { var deferred = storage._current_deferred; // Unblock queue if (deferred !== undefined) { deferred.resolve("Another event added"); } // Add next callback try { storage._service_queue.push(callback); } catch (error) { throw new Error("Cache storage already crashed... " + storage._service_queue.rejectedReason.toString()); } // Block the queue deferred = RSVP.defer(); storage._current_deferred = deferred; storage._service_queue.push(function () { return deferred.promise; }); } function CacheStorage(spec) { this._cache_storage = jIO.createJIO(spec.cache_storage); this._sub_storage = jIO.createJIO(spec.sub_storage); this._service_queue = new RSVP.Queue(); enqueueDefer(this, function () {return; }); } CacheStorage.prototype.get = function () { var context = this, argument_list = arguments; return this._cache_storage.get.apply(this._cache_storage, arguments) .push(undefined, function (error) { if ((error instanceof jIO.util.jIOError) && (error.status_code === 404)) { return context._sub_storage.get.apply(context._sub_storage, argument_list) .push(function (document) { var clone = JSON.parse(JSON.stringify(document)); // XXX Deep clone clone._id = argument_list[0]._id; enqueueDefer(context, function () { return context._cache_storage.put(clone); }); return document; }); } throw error; }); }; CacheStorage.prototype.post = function (param) { var context = this; return this._cache_storage.post.apply(this._cache_storage, arguments) .push(function (id) { // XXX Deep clone param._id = id; enqueueDefer(context, function () { return context._sub_storage.put(param) .push(undefined, function (error) { console.warn(error); console.warn(param); throw error; }); }); return id; }); }; CacheStorage.prototype.put = function () { var context = this, argument_list = arguments; return this._cache_storage.put.apply(this._cache_storage, arguments) .push(function (result) { enqueueDefer(context, function () { return context._sub_storage.put.apply(context._sub_storage, argument_list); }); return result; }); }; CacheStorage.prototype.remove = function () { var context = this, argument_list = arguments; return this._cache_storage.remove.apply(this._cache_storage, arguments) .push(function (result) { enqueueDefer(context, function () { return context._sub_storage.remove.apply(context._sub_storage, argument_list); }); return result; }); }; CacheStorage.prototype.getAttachment = function () { var context = this, argument_list = arguments; return this._cache_storage.getAttachment.apply(this._cache_storage, arguments) .push(undefined, function (error) { if ((error instanceof jIO.util.jIOError) && (error.status_code === 404)) { return context._sub_storage.getAttachment.apply(context._sub_storage, argument_list) .push(function (blob) { enqueueDefer(context, function () { return context._cache_storage.putAttachment(argument_list[0], blob); }); return blob; }); } throw error; }); }; CacheStorage.prototype.putAttachment = function () { var context = this, argument_list = arguments; return this._cache_storage.putAttachment.apply(this._cache_storage, arguments) .push(function (result) { enqueueDefer(context, function () { return context._sub_storage.putAttachment.apply(context._sub_storage, argument_list); }); return result; }); }; CacheStorage.prototype.removeAttachment = function () { var context = this, argument_list = arguments; return this._cache_storage.removeAttachment.apply(this._cache_storage, arguments) .push(function (result) { enqueueDefer(context, function () { return context._sub_storage.removeAttachment.apply(context._sub_storage, argument_list); }); return result; }); }; CacheStorage.prototype.hasCapacity = function () { return this._sub_storage.hasCapacity.apply(this._sub_storage, arguments); }; CacheStorage.prototype.buildQuery = function () { return this._sub_storage.buildQuery.apply(this._sub_storage, arguments); }; jIO.addStorage('cache', CacheStorage); }(jIO));