diff --git a/ui (gen4)/file.js b/ui (gen4)/file.js index c4f1b197..1ed76e97 100755 --- a/ui (gen4)/file.js +++ b/ui (gen4)/file.js @@ -4,8 +4,12 @@ * **********************************************************************/ -var glob = require('glob') var path = require('path') +var events = require('events') + +var fse = require('fs.extra') +var glob = require('glob') +var promise = require('promise') define(function(require){ var module = {} @@ -22,6 +26,41 @@ var tasks = require('lib/tasks') var INDEX_DIR = '.ImageGrid' +/*********************************************************************/ +// Queue +// .enqueue(func) +// .enqueue(task) +// +// .start() +// .stop() +// +// .state +// .size - running pool size +// +// +// Task +// .start(..) +// .stop() +// +// .done(..) +// .fail(..) +// +// .state +// +// Task() +// Task(val) +// Task(val, ...) +// Task([val, ...]) +// +// NOTE: val can be a function or a value... +// ...if value is a promise or a deferred then the task is linked +// to that, and is not startable or resumable... +// +// + + + + /*********************************************************************/ // things we need... // - load latest by pattern @@ -34,25 +73,163 @@ var INDEX_DIR = '.ImageGrid' // - join indexes // - take care of different base paths in images // +// +// // Might also be a nice idea to generic import: // - get all .ImageGrid/*.json -// - group by ([a-z]*).* — pattern with keyword +// - group by ([a-z]*).* — pattern with // - sort by name, descending // - split at first non-diff // - merge diff's in reverse tail to head // -// And output to format: +// ...and output to format: // { // : , // ... // } // +// XXX return a promice rather than an event emitter.... function listIndexes(base){ return glob(base +'/**/'+ INDEX_DIR) } +// XXX return a promice rather than an event emitter.... +function listJSON(path, pattern){ + pattern = pattern || '*' + return glob(path +'/'+ pattern +'.json') +} + + +var loadFile = promise.denodeify(fse.readFile) +function loadJSON(path){ + return readFile(path).then(JSON.parse) +} + + +// json file name format: +// [-][-diff].json +// +// events emited: +// - queued - json file path queued for loading +// - loaded - done loading json file path +// - index - done loding index at path +// - end - done loading all indexes +// +// XXX return a promice rather than an event emitter.... +function loadIndex(path, emitter){ + var p = path.split(INDEX_DIR) + var last = p.slice(-1)[0].trim() + + var end = emitter == null + emitter = emitter == null ? new events.EventEmitter() : emitter + + // we've got an index... + if(p.length > 1 && /^\/*$/.test(last)){ + listJSON(path) + .on('end', function(files){ + var res = {} + var index = {} + // group by keyword... + files + .sort() + .reverse() + .forEach(function(n){ + var s = n.split(/[-.]/g).slice(0, -1) + + // .json / non-diff + if(s.length == 1){ + var k = s[0] + var d = false + + // -[-diff].json / diff / non-diff + } else { + var k = s[1] + var d = s[2] == 'diff' + } + + // new keyword... + if(index[k] == null){ + index[k] = [] + + // do not add anything past the latest non-diff + // for each keyword... + } else if(index[k].slice(-1)[0][0] == false){ + index[k].push([d, n]) + emitter.emit('queued', n) + return + } + + index[k].push([d, n]) + emitter.emit('queued', n) + }) + + // load... + promise + .all(Object.keys(index).map(function(k){ + // get relevant paths... + var diffs = index[k] + var latest = diffs.splice(-1)[0][1] + + // load latest... + return loadJSON(latest) + .then(function(data){ + // handle diffs... + return promise + .all(diffs + .reverse() + .map(function(p){ + p = p[1] + return loadJSON(p) + .done(function(json){ + // merge... + for(var k in json){ + data[k] = json[k] + } + + emitter.emit('loaded', p) + }) + })) + .then(function(){ + res[k] = data + + emitter.emit('loaded', latest) + }) + }) + }) + .then(function(){ + emitter.emit('index', path, res) + + // indicate end only if we are not part of a multi-index load... + if(end){ + emitter.emit('end', {path: res}) + } + }) + }) + + // no explicit index given -- find all in sub tree... + } else { + var res = {} + + // collect the found indexes... + emitter.on('index', function(path, obj){ res[path] = obj }) + + listIndexes(path) + .on('end', function(indexes){ + indexes.forEach(function(path){ loadIndex(path, emitter) }) + + // XXX need to call this when the load was done... + emitter.emit('end', res) + }) + } + + return emitter +} + + + + /********************************************************************** * vim:set ts=4 sw=4 : */ return module }) diff --git a/ui (gen4)/lib/actions.js b/ui (gen4)/lib/actions.js index 79aedd0b..551ca859 100755 --- a/ui (gen4)/lib/actions.js +++ b/ui (gen4)/lib/actions.js @@ -200,13 +200,13 @@ function Action(name, doc, ldoc, func){ // create the actual instance we will be returning... var meth = function(){ - var that = this var args = args2array(arguments) + var that = this var getHandlers = this.getHandlers getHandlers = getHandlers == null ? MetaActions.getHandlers : getHandlers - // get and call handlers -- pre phase... + // get handlers... // // NOTE: using CLASS.__proto__[name].call(this, ...) here is not // possible as there is no reliable way to get the "class" @@ -226,6 +226,7 @@ function Action(name, doc, ldoc, func){ return handlers.slice(-1)[0].apply(this, args) } + // call handlers -- pre phase... handlers = handlers .map(function(h){ return h.apply(that, args) })