Skip to content
This repository has been archived by the owner on Mar 2, 2022. It is now read-only.

Commit

Permalink
somewhat the first version of cached data.
Browse files Browse the repository at this point in the history
  • Loading branch information
simon-scherzinger committed Feb 23, 2016
1 parent 96c914a commit a2f6220
Show file tree
Hide file tree
Showing 3 changed files with 165 additions and 50 deletions.
27 changes: 20 additions & 7 deletions lib/DataManager.js
Original file line number Diff line number Diff line change
Expand Up @@ -674,14 +674,14 @@ DataManager.prototype._requestOptions = function(additionalHeaders) {
};

DataManager.prototype._makeDB = function() {
if (this._db) {
return Promise.resolve(this._db);
}
this._db = new loki(this.id + '.db.json', {
autosave: true,
autosaveInterval: 30000
});
return new Promise(function(resolve, reject) {
if (this._db) {
return resolve(this._db);
}
this._db = new loki(this.id + '.db.json', {
autosave: true,
autosaveInterval: 30000
});
this._db.loadDatabase({}, function(err) {
if (err && err.message.indexOf('ENOENT') !== -1) {
return this._db.saveDatabase(function(err) {
Expand All @@ -696,6 +696,19 @@ DataManager.prototype._makeDB = function() {
}
return resolve(this._db);
}.bind(this));
}.bind(this))
.then(function(db) {
this._cacheMetaData = db.getCollection('_metadata');
if (!this._cacheMetaData) {
this._cacheMetaData = db.addCollection('_metadata', {
indices: [
'etag',
'created',
'title'
]
});
}
return Promise.resolve(db);
}.bind(this));
};

Expand Down
68 changes: 53 additions & 15 deletions lib/Model.js
Original file line number Diff line number Diff line change
Expand Up @@ -18,43 +18,49 @@ var Model = function(title, metadata, dm) {

Model.prototype.enableCache = function(maxCacheAge) {
return this._dm._makeDB().then(function(db) {
this._collection = db.getCollection(this.title);
if (!this._collection) {
this._collection = db.addCollection(this.title, {
this._maxAge = maxCacheAge || 600000;
this._items = db.getCollection(this.title) || db.addCollection(this.title, {
indices: [
'_id',
'_entryTitle'
]
});
}
//this._items.ensureUniqueIndex('_id');
return this._loadData();
}.bind(this)).catch(function(err) {
throw err;
});
}.bind(this));
};

Model.prototype._loadData = function() {
return new Promise(function(resolve, reject) {
this._getTraversal().then(function(traversal) {
return this._getTraversal()
.then(function(traversal) {
return new Promise(function(resolve, reject) {
traversal.continue().newRequest()
.follow(this._dm.id + ':' + this.title)
.withRequestOptions(this._dm._requestOptions())
.withTemplateParameters({ size: 0 })
.get(function(err, res, traversal) {
util.checkResponse(err, res).then(function(res) {
return util.checkResponse(err, res)
.then(function(res) {
var body = halfred.parse(JSON.parse(res.body));
var entries = body.embeddedResourceArray(this._dm.id + ':' + this.title);
this._collection.removeDataOnly();
this._items.removeDataOnly();
for (var i = 0; i < entries.length; i++) {
this._collection.insert(entries[i]);
this._items.insert(entries[i].original());
}
this._dm._cacheMetaData.removeWhere({ title: this.title });
this._dm._cacheMetaData.insert({
title: this.title,
etag: res.headers.etag,
created: new Date().toISOString()
});
this._dm._db.save(function(err) {
if (err) {
return reject(err);
}
return resolve(this);
}.bind(this))
}.bind(this)).catch(reject);
return resolve(this._items);
}.bind(this));
}.bind(this))
.catch(reject);
}.bind(this));
}.bind(this));
}.bind(this));
Expand Down Expand Up @@ -88,6 +94,15 @@ Model.prototype._getTraversal = function() {
});
};

Model.prototype._ensureNotStale = function() {
var maxAge = new Date().getTime() - this._maxAge;
var created = new Date(this._dm._cacheMetaData.find({ title: this.title })[0].created).getTime();
if (created > maxAge) {
return Promise.resolve(this._items);
}
return this._loadData();
};

Model.prototype.resolve = function() {
var model = this;
return new Promise(function(resolve, reject) {
Expand Down Expand Up @@ -132,6 +147,29 @@ Model.prototype.getSchema = function(method) {

Model.prototype.entryList = function(options) {
var model = this;
if (this._maxAge) {
return Promise.resolve()
.then(function() {
switch (options.cacheType || 'default') {
case 'stale':
throw new Error('cacheType \'stale\' not implemented.');
case 'refresh':
return this._loadData();
case 'default':
default:
return this._ensureNotStale();
}
}.bind(this))
.then(function(items) {
var res = items.find('getAll');
var out = [];
for (var i = 0; i < res.length; i++) {
out.push(new Entry(halfred.parse(res[i]), this._dm, this));
}
return Promise.resolve({ entries: out, count: out.length, total: items.data.length })
}.bind(this));
}

return this._getTraversal().then(function(traversal) {
return new Promise(function(resolve, reject) {
var t = traversal.continue().newRequest()
Expand Down
120 changes: 92 additions & 28 deletions test/sdk.test.js
Original file line number Diff line number Diff line change
Expand Up @@ -468,40 +468,104 @@ describe('model', function() {
});
});

describe('offline model', function() {
var dm;
beforeEach(function() {
dm = new DataManager({
url: baseUrl + '58b9a1f5'
if (isNode) {
describe('offline model', function() {
var dm;
beforeEach(function() {
dm = new DataManager({
url: baseUrl + '58b9a1f5'
});
});
});
afterEach(function() {
dm = null;
});
it('make single model offline by dm', function() {
return dm.enableCache('to-do-list').then(function(models) {
expect(models[0]).to.be.a('object');
expect(models[0].id).to.be.equal('to-do-list');
expect(models[0]._collection).to.be.a('object');
afterEach(function() {
dm = null;
});
it('make single model offline by dm', function() {
return dm.enableCache('to-do-list').then(function(models) {
expect(dm._cacheMetaData).to.be.a('object');
expect(models[0]).to.be.a('object');
expect(models[0].name).to.be.equal('to-do-list');
});
});
it('make single model offline by model', function() {
return dm.model('to-do-list').enableCache().then(function(model) {
expect(dm._cacheMetaData).to.be.a('object');
expect(model).to.be.a('object');
expect(model.name).to.be.equal('to-do-list');
});
});
it('make multiple models offline by dm', function() {
return dm.enableCache([
'to-do-list',
'to-do-item'
]).then(function(models) {
expect(models).to.be.a('array');
expect(models.length).to.be.equal(2);
}).catch();
});
});
it('make single model offline by model', function() {
return dm.model('to-do-list').enableCache().then(function(model) {
expect(model).to.be.a('object');
expect(model.id).to.be.equal('to-do-list');
expect(model._collection).to.be.a('object');
describe('stale data', function() {
var dm;
beforeEach(function(done) {
dm = new DataManager({
url: baseUrl + '58b9a1f5'
});
dm.enableCache([
'to-do-item',
'to-do-list'
], 1)
.then(function() {
done();
})
.catch(done);
});
afterEach(function() {
dm = null;
});
it('entries size 0', function() {
return dm.model('to-do-list').entries({ size: 0 })
.then(function(entries) {
expect(entries.length).to.be.equal(2);
});
});
});
it('make multiple models offline by dm', function() {
return dm.enableCache([
'to-do-list',
'to-do-item'
]).then(function(models) {
expect(models).to.be.a('array');
expect(models.length).to.be.equal(2);
}).catch();
describe('valid cache data', function() {
var dm;
beforeEach(function(done) {
dm = new DataManager({
url: baseUrl + '58b9a1f5'
});
dm.enableCache([
'to-do-item',
'to-do-list'
])
.then(function() {
done();
})
.catch(done);
});
afterEach(function() {
dm = null;
});
it('entries size 0', function() {
return dm.model('to-do-list').entries({ size: 0 })
.then(function(entries) {
expect(entries.length).to.be.equal(2);
});
});
it('entries size 0', function() {
return dm.model('to-do-list').entries({ size: 0, cacheType: 'refresh' })
.then(function(entries) {
expect(entries.length).to.be.equal(2);
});
});
it.skip('entries size 0', function() {
return dm.model('to-do-list').entries({ size: 0, cacheType: 'stale' })
.then(function(entries) {
expect(entries.length).to.be.equal(2);
});
});
});
});
}

describe('entry/entries', function() { // this is basically modelList
var dm;
Expand Down

0 comments on commit a2f6220

Please sign in to comment.