Skip to content

Instantly share code, notes, and snippets.

@kfranqueiro
Created March 29, 2011 12:39
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save kfranqueiro/892290 to your computer and use it in GitHub Desktop.
Save kfranqueiro/892290 to your computer and use it in GitHub Desktop.
Possibly-naive attempt at a generic dojo.store wrapper supporting getChildren, via parent relationships.
/*
NOTE: This wrapper "works", but is sorta incomplete...
* It does not explicitly support deterministic ordering/rearrangement of children.
* For that matter, the way Tree currently achieves this seems sort of obtuse.
Tree makes a blatant assumption on the existence of a children attribute
(since there is no dedicated method to set them), and reconstructs the array
every time children are reordered...
* It's also probably sorta inefficient, but it was my (perhaps naive) attempt
at making a generic wrapper that could fit multiple stores (and indeed it
does work at least on dojo.store.Memory and kgf.lawnchair.LawnchairStore).
Perhaps the thought of a generic wrapper providing getChildren is unrealistic?
*/
dojo.provide('kgf.store.ParentHierarchical');
kgf.store.ParentHierarchical = function(store, options) {
//Wraps a store with simple support for ancestry via a single
//upwards-hierarchical attribute specifying the parent node's ID.
//The attribute's name may be specified by options.parentAttr.
//NOTE: this implementation implements getChildren via query.
//Therefore, getChildren will be subject to any caching, etc.
//present in the query implementation.
var
parentAttr = (options && options.parentAttr) || 'parentId',
oldQuery = store.query;
function wrapWrite(func) {
return function(object, options) {
if (options && options.parentId) {
object[parentAttr] = options.parentId;
}
func.call(this, object, options);
};
}
//add getChildren method
store.getChildren = function(object, options) {
var q = {};
q[parentAttr] = this.getIdentity(object);
return this.query(q, { deep: false });
};
//add getParent method (out of spec, but it's easy!)
store.getParent = function(object) {
return this.get(object[parentAttr]);
};
//also add support for options.parentId to add/put methods
store.add = wrapWrite(store.add);
store.put = wrapWrite(store.put);
//wrap query method to filter adequately
store.query = function(query, options) {
var q = query;
if (!(options && options.deep) && !q.hasOwnProperty(parentAttr)) {
//not a deep query - limit to top-level items.
if (typeof q == 'function') { //e.g. SimpleQueryEngine
q = function(item) {
if (typeof item[parentAttr] == 'undefined') {
return false;
}
return query(item);
};
} else if (dojo.isObject(q)) {
q = (q ? dojo.clone(q) : {});
q[parentAttr] = undefined; //sneaky, but seems to work
}
}
return oldQuery.call(store, q, options);
};
return store;
};
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment