Created
April 27, 2012 18:50
-
-
Save atuttle/2511809 to your computer and use it in GitHub Desktop.
All I've done here is taken the pagination plugin and mashed it into the query plugin, so that we can have the awesomeness of .where(...).page(...)
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
// - NOT jsonPath or jsonQuery which are horrendously complex and fugly | |
// - simple query syntax 'its just javascript' | |
// - simple string interpolation | |
// - search then sorting | |
Lawnchair.plugin((function(){ | |
// | |
var interpolate = function(template, args) { | |
var parts = template.split('?').filter(function(i) { return i != ''}) | |
, query = '' | |
for (var i = 0, l = parts.length; i < l; i++) { | |
query += parts[i] + args[i] | |
} | |
return query | |
} | |
var sorter = function(p) { | |
return function(a, b) { | |
if (a[p] < b[p]) return -1 | |
if (a[p] > b[p]) return 1 | |
return 0 | |
} | |
} | |
// | |
return { | |
// query the storage obj | |
where: function() { | |
// ever notice we do this sort thing lots? | |
var args = [].slice.call(arguments) | |
, tmpl = args.shift() | |
, last = args[args.length - 1] | |
, qs = tmpl.match(/\?/g) | |
, q = qs && qs.length > 0 ? interpolate(tmpl, args.slice(0, qs.length)) : tmpl | |
, is = new Function(this.record, 'return !!(' + q + ')') | |
, r = [] | |
, cb | |
// iterate the entire collection | |
// TODO should we allow for chained where() to filter __results? (I'm thinking no b/c creates funny behvaiors w/ callbacks) | |
this.all(function(all){ | |
for (var i = 0, l = all.length; i < l; i++) { | |
if (is(all[i])) r.push(all[i]) | |
} | |
}) | |
// overwrite working results | |
this.__results = r | |
// callback / chain | |
if (args.length === 1) this.fn(this.name, last).call(this, this.__results) | |
return this | |
}, | |
// FIXME should be able to call without this.__results | |
// ascending sort the working storage obj on a property (or nested property) | |
asc: function(property, callback) { | |
this.fn(this.name, callback).call(this, this.__results.sort(sorter(property))) | |
return this | |
}, | |
// descending sort on working storage object on a property | |
desc: function(property, callback) { | |
this.fn(this.name, callback).call(this, this.__results.sort(sorter(property)).reverse()) | |
return this | |
}, | |
//mash in the page method from the pagination plugin | |
page: function (page, callback) { | |
// some defaults | |
var objs = [] | |
, count = 5 // TODO make this configurable | |
, cur = ~~page || 1 | |
, next = cur + 1 | |
, prev = cur - 1 | |
, start = cur == 1 ? 0 : prev*count | |
, end = start >= count ? start+count : count | |
// grab all the records | |
// FIXME if this was core we could use this.__results for faster queries | |
objs = this.__results | |
// grab the metadata | |
var max = Math.ceil(objs.length/count) | |
, page = { max: max | |
, next: next > max ? max : next | |
, prev: prev == 0 ? 1 : prev | |
} | |
// reassign to the working resultset | |
this.__results = page[this.name] = objs.slice(start, end) | |
// callback / chain | |
if (callback) this.fn('page', callback).call(this, page) | |
return this | |
} | |
} | |
///// | |
})()) |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment