lpushmanager.js | |
|---|---|
var fs = require('fs')
, path = require('path')
, lconfig = require("lconfig")
, ldatastore = require('ldatastore')
, datastore = {}
, async = require('async')
, datasets = {}
, levents = require('levents')
, lutil = require('lutil')
, config = {}
; | |
| this works, but feels like it should be a cleaner abstraction layer on top of the datastore instead of this garbage | datastore.init = function(callback) {
ldatastore.init('push', callback);
}
datastore.addCollection = function(dataset) {
ldatastore.addCollection('push', dataset, 'push', 'id');
}
datastore.removeObject = function(dataset, id, ts, callback) {
if (typeof(ts) === 'function') {
ldatastore.removeObject('push', 'push_' + dataset, id, {timeStamp: Date.now()}, ts);
} else {
ldatastore.removeObject('push', 'push_' + dataset, id, ts, callback);
}
}
datastore.addObject = function(dataset, obj, ts, callback) {
ldatastore.addObject('push', 'push_' + dataset, obj, ts, callback);
}
config.datasets = {};
module.exports.datasets = config.datasets;
module.exports.init = function () {
var dir = path.join(lconfig.me, "push");
if (!path.existsSync(lconfig.me)) fs.mkdirSync(lconfig.me, 0755);
if (!path.existsSync(dir)) fs.mkdirSync(path.join(lconfig.me, "push"), 0755);
if (!path.existsSync(path.join(dir, "push_config.json"))) return;
config = JSON.parse(fs.readFileSync(path.join(dir, "push_config.json")));
module.exports.datasets = config.datasets;
}
module.exports.acceptData = function(dataset, response, callback) {
datastore.init(function() {
var deletedIDs = {};
if (response.config) {
if (config[dataset]) {
deletedIDs = compareIDs(config[dataset], response.config);
} else {
config[dataset] = {};
}
lutil.extend(true, config[dataset], response.config);
lutil.atomicWriteFileSync(path.join(lconfig.lockerDir, lconfig.me, "push", 'push_config.json'),
JSON.stringify(config, null, 4));
}
if (typeof(response.data) === 'string') {
return callback('data is in a wacked out format');
}
if (dataset.length === 0) {
return callback();
}
processData(deletedIDs, response.data, dataset, callback);
});
} |
| copy copy copy | function compareIDs (originalConfig, newConfig) {
var resp = {};
if (originalConfig && originalConfig.ids && newConfig && newConfig.ids) {
var newSet = newConfig.ids;
var oldSet = originalConfig.ids;
var seenIDs = {};
resp = [];
for (var j = 0; j < newSet.length; j++) seenIDs[newSet[j]] = true;
for (var j = 0; j < oldSet.length; j++) {
if (!seenIDs[oldSet[j]]) resp.push(oldSet[j]);
}
}
return resp;
} |
| dataset is the name of the dataset | function processData (deleteIDs, data, dataset, callback) {
if (!module.exports.datasets[dataset]) {
module.exports.datasets[dataset] = true;
lutil.atomicWriteFileSync(path.join(lconfig.lockerDir, lconfig.me, "push", 'push_config.json'),
JSON.stringify(config, null, 4));
}
datastore.addCollection(dataset);
if (deleteIDs && deleteIDs.length > 0 && data) {
addData(dataset, data, function(err) {
if(err) {
callback(err);
} else {
deleteData(dataset, deleteIDs, callback);
}
});
} else if (data && data.length > 0) {
addData(dataset, data, callback);
} else if (deleteIDs && deleteIDs.length > 0) {
deleteData(dataset, deleteIDs, callback);
} else {
callback();
}
}
function deleteData (dataset, deleteIds, callback) {
var q = async.queue(function(id, cb) {
levents.fireEvent(lutil.idrNew(dataset, 'push', id), 'delete');
datastore.removeObject(dataset, id, cb);
}, 5);
deleteIds.forEach(q.push);
q.drain = callback;
}
function addData (dataset, data, callback) {
var errs = [];
var q = async.queue(function(item, cb) {
var object = (item.obj) ? item : {obj: item};
if (object.obj) {
if(object.obj.id === null || object.obj.id === undefined) {
errs.push({"message":"no value for primary key", "obj": object.obj});
return cb();
}
if (object.type === 'delete') {
levents.fireEvent(lutil.idrNew(dataset, 'push', object.obj.id), 'delete');
datastore.removeObject(dataset, object.obj["id"], {timeStamp: object.timestamp}, cb);
} else {
datastore.addObject(dataset, object.obj, {timeStamp: object.timestamp}, function(err, type, doc) {
if (type === 'same') return cb();
levents.fireEvent(lutil.idrNew(dataset, 'push', object.obj.id), type, doc);
return cb();
});
}
} else {
cb();
}
}, 5);
data.forEach(function(d){ q.push(d, errs.push); }); // hehe fun
q.drain = function() {
if (errs.length > 0) {
callback(errs);
} else {
callback();
}
};
}
|