Skip to content

HTTPS clone URL

Subversion checkout URL

You can clone with
or
.
Download ZIP
Browse files

Fixed sorting logic, fixed data tracking in memory, added unit tests,…

… added Cache store wrapper, refs #11537
  • Loading branch information...
commit 9768667176f9632db118bf4169fb22d1adfff032 1 parent fde4406
@kriszyp kriszyp authored
View
51 store/Cache.js
@@ -0,0 +1,51 @@
+define("dojo/store/Cache", ["dojo"], function(dojo) {
+
+dojo.store.Cache = function(masterStore, cachingStore, options){
+ // summary:
+ // The Cache store wrapper takes a master store and a caching store,
+ // caches data from the master into the caching store for faster
+ // lookup. Normally one would use a memory store for the caching
+ // store and a server store like JsonRest for the master store.
+ var store = dojo.mixin({}, masterStore);
+ options = options || {};
+ store.query = function(query, directives){
+ if(options.canQueryCache && options.canQueryCache(query, directives)){
+ return cachingStore.query(query, directives);
+ }
+ var results = masterStore.query(query, directives);
+ results.forEach(function(object){
+ if(!options.isLoaded || options.isLoaded(object)){
+ cachingStore.put(object);
+ }
+ });
+ return results;
+ };
+ store.get = function(id, directives){
+ return dojo.when(cachingStore.get(id), function(result){
+ return result || dojo.when(masterStore.get(id, directives), function(result){
+ if(result){
+ cachingStore.put(result, {id: id});
+ }
+ return result;
+ });
+ });
+ };
+ store.add = function(object, directives){
+ cachingStore.add(object, directives);
+ return masterStore.add(object, directives);
+ };
+ store.put = function(object, directives){
+ cachingStore.put(object, directives);
+ return masterStore.put(object, directives);
+ };
+ store.remove = function(id, directives){
+ cachingStore.remove(id, directives);
+ return masterStore.remove(id, directives);
+ };
+ store.evict = function(id){
+ cachingStore.remove(id);
+ }
+ return store;
+};
+return dojo.store.Cache;
+});
View
17 store/Memory.js
@@ -46,6 +46,15 @@ dojo.store.Memory = function(options){
// The identity to use for storing the data
id = options && options.id || object[this.idProperty] || Math.random();
this.index[id] = object;
+ var data = this.data,
+ idProperty = this.idProperty;
+ for(var i = 0, l = data.length; i < l; i++){
+ if(data[i][idProperty] == id){
+ data[i] = object;
+ return;
+ }
+ }
+ this.data.push(object);
},
add: function(object, options){
// summary:
@@ -67,6 +76,14 @@ dojo.store.Memory = function(options){
// id:
// The identity to use to delete the object
delete this.index[id];
+ var data = this.data,
+ idProperty = this.idProperty;
+ for(var i = 0, l = data.length; i < l; i++){
+ if(data[i][idProperty] == id){
+ data.splice(i, 1);
+ return;
+ }
+ }
},
query: function(query, options){
// summary:
View
2  store/util/SimpleQueryEngine.js
@@ -31,7 +31,7 @@ dojo.store.util.SimpleQueryEngine = function(query, options){
var aValue = a[sort.attribute];
var bValue = b[sort.attribute];
if (aValue != bValue) {
- return sort.descending == aValue > bValue ? -1 : 1;
+ return !!sort.descending == aValue > bValue ? -1 : 1;
}
}
return 0;
View
88 tests/store/Cache.js
@@ -0,0 +1,88 @@
+dojo.provide("dojo.tests.store.Cache");
+dojo.require("dojo.store.Memory");
+dojo.require("dojo.store.Cache");
+(function(){
+ var masterStore = new dojo.store.Memory({
+ data: [
+ {id: 1, name: "one", prime: false},
+ {id: 2, name: "two", even: true, prime: true},
+ {id: 3, name: "three", prime: true},
+ {id: 4, name: "four", even: true, prime: false},
+ {id: 5, name: "five", prime: true}
+ ]
+ });
+ var cachingStore = new dojo.store.Memory();
+ var options = {};
+ var store = dojo.store.Cache(masterStore, cachingStore, options);
+ tests.register("dojo.tests.store.Cache",
+ [
+ function testGet(t){
+ t.is(store.get(1).name, "one");
+ t.is(cachingStore.get(1).name, "one"); // second one should be cached
+ t.is(store.get(1).name, "one");
+ t.is(store.get(4).name, "four");
+ t.is(cachingStore.get(4).name, "four");
+ t.is(store.get(4).name, "four");
+ },
+ function testQuery(t){
+ options.isLoaded = function(){ return false;};
+ t.is(store.query({prime: true}).length, 3);
+ t.is(store.query({even: true})[1].name, "four");
+ t.is(cachingStore.get(3), undefined);
+ options.isLoaded = function(){ return true;};
+ t.is(store.query({prime: true}).length, 3);
+ t.is(cachingStore.get(3).name, "three");
+ t.is(store.query({prime: false}).length, 2);
+ options.canQueryCache = function(){
+ return true;
+ };
+ t.is(store.query({prime: true}).length, 3);
+ },
+ function testQueryWithSort(t){
+ t.is(store.query({prime: true}, {sort:[{attribute:"name"}]}).length, 3);
+ t.is(store.query({even: true}, {sort:[{attribute:"name"}]})[1].name, "two");
+ },
+ function testPutUpdate(t){
+ var four = store.get(4);
+ four.square = true;
+ store.put(four);
+ four = store.get(4);
+ t.t(four.square);
+ four = cachingStore.get(4);
+ t.t(four.square);
+ four = masterStore.get(4);
+ t.t(four.square);
+ },
+ function testPutNew(t){
+ store.put({
+ id: 6,
+ perfect: true
+ });
+ t.t(store.get(6).perfect);
+ t.t(cachingStore.get(6).perfect);
+ t.t(masterStore.get(6).perfect);
+ },
+ function testAddDuplicate(t){
+ var threw;
+ try{
+ store.add({
+ id: 6,
+ perfect: true
+ });
+ }catch(e){
+ threw = true;
+ }
+ t.t(threw);
+ },
+ function testAddNew(t){
+ store.add({
+ id: 7,
+ prime: true
+ });
+ t.t(store.get(7).prime);
+ t.t(cachingStore.get(7).prime);
+ t.t(masterStore.get(7).prime);
+ }
+ ]
+ );
+})();
View
8 tests/store/Memory.js
@@ -62,6 +62,14 @@ dojo.require("dojo.store.Memory");
});
t.t(store.get(7).prime);
},
+ function testRemove(t){
+ store.remove(7);
+ t.is(store.get(7), undefined);
+ },
+ function testQueryAfterChanges(t){
+ t.is(store.query({prime: true}).length, 3);
+ t.is(store.query({perfect: true}).length, 1);
+ },
function testIFRSStyleData(t){
var anotherStore = new dojo.store.Memory({
data: {
Please sign in to comment.
Something went wrong with that request. Please try again.