Commit b0f722a0 by Guillaume Royer

feat(elasticlunr storage): handle multiple tab shared index

- use localStorage to notify changes between tabs on the same domain
parent e0efbb85
......@@ -19,11 +19,30 @@
*/
/*jslint sloppy: true, nomen: true */
/*global jIO, RSVP, Blob, Query, elasticlunr */
(function (jIO, RSVP, Blob, Query, elasticlunr) {
/*global jIO, RSVP, Blob, Query, elasticlunr, localStorage */
(function (jIO, RSVP, Blob, Query, elasticlunr, localStorage) {
'use strict';
var elasticlunrStorageKey = 'jio_elasticlunr';
var elasticlunrStorageKey = 'jio_elasticlunr',
notifyChangeKey = elasticlunrStorageKey + '_notify';
function notifyIndexChanged() {
localStorage.setItem(notifyChangeKey, JSON.stringify({
type: 'update',
date: new Date()
}));
// no need to keep the actual value
localStorage.removeItem(notifyChangeKey);
}
function listenIndexChanged(context) {
window.addEventListener('storage', function (event) {
// since we remove the item after setting it, make sure we only run once
if (event.newValue && event.key === notifyChangeKey) {
context._onIndexChanged();
}
});
}
function findDuplicates(array) {
var sorted = array.slice().sort(),
......@@ -149,8 +168,16 @@
this._sub_storage.__type;
this._index_id = spec.id || 'id';
this._index_fields = spec.index_fields || [];
listenIndexChanged(this);
}
ElasticlunrStorage.prototype._onIndexChanged = function () {
// force-reload index from storage
this._index = null;
this._getIndex();
};
ElasticlunrStorage.prototype._getIndex = function () {
var context = this;
......@@ -181,6 +208,9 @@
ElasticlunrStorage.prototype._saveIndex = function () {
var context = this;
// notify other tabs that the index has changed
notifyIndexChanged();
return this._getIndex()
.push(function (index) {
var data = JSON.stringify(index);
......@@ -336,4 +366,4 @@
};
jIO.addStorage('elasticlunr', ElasticlunrStorage);
}(jIO, RSVP, Blob, Query, elasticlunr));
}(jIO, RSVP, Blob, Query, elasticlunr, localStorage));
/*jslint nomen: true */
/*global jIO, QUnit, sinon, Blob, elasticlunr */
(function (jIO, QUnit, sinon, Blob, elasticlunr) {
/*global jIO, QUnit, sinon, Blob, elasticlunr, localStorage */
(function (jIO, QUnit, sinon, Blob, elasticlunr, localStorage) {
"use strict";
var test = QUnit.test,
stop = QUnit.stop,
......@@ -1261,7 +1261,15 @@
/////////////////////////////////////////////////////////////////
// ElasticlunrStorage.__storage._saveIndex
/////////////////////////////////////////////////////////////////
module("ElasticlunrStorage.__storage._saveIndex");
module("ElasticlunrStorage.__storage._saveIndex", {
setup: function () {
this.notifyIndexChangedStub = sinon.stub(localStorage, "setItem");
},
teardown: function () {
this.notifyIndexChangedStub.restore();
delete this.notifyIndexChangedStub;
}
});
test("stores index as attachment", function () {
Index200.prototype.getAttachment = function () {
......@@ -1277,7 +1285,8 @@
type: "elasticlunr200"
}
}),
blob = new Blob(["{}"]);
blob = new Blob(["{}"]),
context = this;
jio.__storage._getIndex = function () {
return new RSVP.Queue().push(function () {
......@@ -1301,11 +1310,15 @@
};
stop();
expect(4);
expect(5);
jio.__storage._saveIndex()
.then(function (result) {
equal(result, "OK");
ok(
context.notifyIndexChangedStub.called,
"load index count " + context.callCount
);
})
.fail(function (error) {
ok(false, error);
......@@ -1314,4 +1327,4 @@
start();
});
});
}(jIO, QUnit, sinon, Blob, elasticlunr));
}(jIO, QUnit, sinon, Blob, elasticlunr, localStorage));
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or sign in to comment