[dojo-contributors] Regarding dojo.data.fetch queries...

Brian Douglas Skinner skinner at dojotoolkit.org
Thu Aug 16 14:42:16 EDT 2007


Hi Tom,

> ...looking through the code, I'm trying to figure out how to 
> write a query that is hierarchical in nature, and from what 
> I'm seeing in the code (ItemFileReadStore), I'm not sure this 
> is possible without writing a filtering mechanism after getting 
> the query results. Say I have a structure like so:
> 
> Book
>     -- Chapter
>         -- Section
>             -- Paragraphs
> 
> ...and I have several chapters.  What I'm trying to do is something 
> like the following (in English):
> 
> "Get me all of the Paragraphs in the first Chapter".
> 
> Is such a thing possible without going through some major workarounds 
> (like querying the chapters, manually finding the first one and then 
> traversing down the item.children tree)?


Short answer:

If you're using ItemFileReadStore, you'll probably want to use a simple 
mixin to add a getValuesByPath() function to your datastore, so that you 
can then do something like this:

var chap1 = store.getValue(book, chapters);
var array = store.getValuesByPath(chap1, "sections/paragraphs");



Long answer:

It depends on what datastore you're using.  One of the design goals for 
the dojo.data APIs was to make it possible to have many different 
datastores that connect to a wide variety of different types of data 
sources (web services, RDBMSs, XML databases, RDF servers, etc.). 
Different types of data sources have wildly different query languages 
and query semantics, so we figured it probably wasn't realistic to try 
to standardize on a single dojo.data query syntax, since coming up with 
that unified field theory of queries could easily be a PhD thesis.  In 
the API spec for the fetch() method, we explicitly do not specify the 
syntax or semantics for the query.  Each datastore is free to use 
whatever native query system is available on the server that datastore 
connects to.

If you're using ItemFileReadStore, its query logic does not have support 
for the sort of hierarchical query you're looking for.  With 
ItemFileReadStore, you'll have to first get the chapter you want and 
then traverse down to get the list of paragraphs.

Back in the April IRC meetings we talked about the idea of having a 
standard mechanism in dojo.data for easily getting a list of 
nested/children like in your example.  We thought about adding a nested 
traversal requirement to the Read API itself, and requiring all 
datastores to implement it, but that would have added complexity to the 
basic Read API and made it harder for people to write simple datastores.

Instead, we came up with a simple mixin function that can be applied to 
any datastore to add path-based access.  Here's what using that mixin 
function would look like for the example you gave above, "Get me all of 
the Paragraphs in the first Chapter":

var chap1 = store.getValue(book, chapters);
var array = store.getValuesByPath(chap1, "sections/paragraphs");

And here's what the mixin function itself might look like:

getValuesByPath = function(item, /*Array||String*/ path){
     var pathArray;
     if(dojo.isArray(path)){
         pathArray = path;
     }
     if(dojo.isString(path)){
         pathArray = path.split('/');
     }
     var pending = [item];
     var results = null;
     for(var i = 0; i < pathArray.length; ++i){
         results = [];
         for(var j = 0; j < pending.length; ++j){
             var more = store.getValues(pending[j], pathArray[i]);
             results = results.concat(more);
         }
         pending = results;
     }
     return (results || []);
};

We don't yet have a mixin function like that available in 
dojo.data.util, but we could add it there if it seems generally useful.

:o) Brian




More information about the dojo-contributors mailing list