mirror of
/repos/Prototyper.git
synced 2025-12-30 06:31:32 +01:00
203 lines
6.4 KiB
JavaScript
203 lines
6.4 KiB
JavaScript
'use strict';
|
|
var ObjectID = require('mongodb').ObjectID;
|
|
var _ = require('underscore');
|
|
|
|
|
|
module.exports = function (config, db) {
|
|
|
|
// config.database.pk = '_id'
|
|
|
|
/*
|
|
* options:
|
|
* collection (mandatory)
|
|
* query (mandatory)
|
|
*/
|
|
function getMongoContent(options, callback) {
|
|
config.debug && config.debug('getMongoContent options', options);
|
|
if (!options.collection) {
|
|
return callback && callback(new Error('Data not found / missing collection'));
|
|
}
|
|
return db.collection(options.collection, function collection(err, col) {
|
|
if (err) {
|
|
config.error && config.error('ERR2 getMongoContent', err);
|
|
return callback && callback(err);
|
|
}
|
|
if (!options.query) {
|
|
return callback && callback(new Error('Data not found ' + options.collection + ' / missing query'), null, col);
|
|
}
|
|
if (options.query._id && !(options.query._id instanceof Object)) {
|
|
try {
|
|
options.query._id = new ObjectID.createFromHexString(options.query._id);
|
|
} catch (error) {
|
|
config.error && config.error('ERR3 getMongoContent', error);
|
|
return callback && callback(error);
|
|
}
|
|
}
|
|
return col.findOne(options.query, function foundOne(err, result) {
|
|
if (err) {
|
|
config.error && config.error('ERR4 getMongoContent', err);
|
|
return callback && callback(err);
|
|
}
|
|
if (!result) {
|
|
return callback && callback(new Error('Data not found ' + options.collection + '/' + JSON.stringify(options.query)), null, col);
|
|
}
|
|
return callback && callback(null, result, col);
|
|
});
|
|
});
|
|
}
|
|
|
|
|
|
/*
|
|
* options:
|
|
* collection (mandatory)
|
|
* query (mandatory)
|
|
* attribute (mandatory)
|
|
*/
|
|
function getMongoAttribute(options, callback) {
|
|
config.debug && config.debug('getMongoAttribute options', options);
|
|
return getMongoContent(options, function document(err, result, col) {
|
|
if (err) {
|
|
config.error && config.error('ERR1 getMongoAttribute', err);
|
|
return callback && callback(err);
|
|
}
|
|
if (!options.attribute) {
|
|
return callback && callback(new Error('Data not found / ' + options.collection + '/' + JSON.stringify(options.query) + ' missing attribute', null, col));
|
|
}
|
|
var attribute_options = null;
|
|
config.debug && config.debug('getMongoAttribute result', result);
|
|
if (result &&
|
|
result.hasOwnProperty(options.attribute) &&
|
|
result[options.attribute].guid) {
|
|
attribute_options = {
|
|
collection: options.collection,
|
|
query: {_id: result[options.attribute].guid}
|
|
};
|
|
config.debug && config.debug('getMongoAttribute attribute_options', attribute_options);
|
|
|
|
getMongoContent(attribute_options, function attribute(err, attribute_result, coll) {
|
|
if (err) {
|
|
config.error && config.error('ERR2 getMongoAttribute', err);
|
|
return callback && callback(err);
|
|
}
|
|
config.debug && config.debug('getMongoAttribute attribute_result', attribute_result);
|
|
return callback && callback(err, attribute_result, coll);
|
|
});
|
|
} else {
|
|
config.debug && config.debug('getMongoAttribute try direct lookup');
|
|
attribute_options = {
|
|
collection: options.collection,
|
|
query: {
|
|
parent: result._id,
|
|
name: result.name + '.' + options.attribute
|
|
}
|
|
};
|
|
config.debug && config.debug('getMongoAttribute attribute_options', attribute_options);
|
|
|
|
return getMongoContent(attribute_options, function attribute(err, attribute_result, coll) {
|
|
if (err) {
|
|
config.error && config.error('ERR getMongoAttribute', err);
|
|
return callback && callback(err);
|
|
}
|
|
config.debug && config.debug('getMongoAttribute direct attribute_result', attribute_result);
|
|
return callback && callback(err, attribute_result, coll);
|
|
});
|
|
}
|
|
});
|
|
}
|
|
|
|
function saveData(collection, data, callback) {
|
|
if (data._id && !(data._id instanceof Object)) {
|
|
data._id = new ObjectID.createFromHexString(data._id);
|
|
}
|
|
config.debug && config.debug('saveData saving', data._id);
|
|
collection.save(data, {safe: true}, function (err, result2, result3) {
|
|
if (err) {
|
|
config.error && config.error('ERR saveData', err);
|
|
return callback && callback(err);
|
|
|
|
}
|
|
config.debug && config.debug('saveData saved', data._id, result2, result3);
|
|
return callback && callback(null, data, collection);
|
|
});
|
|
}
|
|
|
|
var updating = false;
|
|
|
|
function updateData(collection, data, callback) {
|
|
if (updating) {
|
|
//noinspection JSUnresolvedFunction
|
|
setImmediate(function rescheduling() {
|
|
config.debug && config.debug('Updating, rescheduling');
|
|
return updateData(collection, data, callback);
|
|
});
|
|
} else {
|
|
updating = true;
|
|
var stopUpdating = function (err, result, col) {
|
|
config.debug && config.debug('Stop updating');
|
|
updating = false;
|
|
if (err) {
|
|
return callback && callback(err);
|
|
}
|
|
return callback && callback(null, result, col);
|
|
};
|
|
|
|
return collection.findOne({_id: data._id}, function foundOne(err, result) {
|
|
if (err) {
|
|
config.error && config.error('ERR updateData', err);
|
|
return callback && callback(err);
|
|
}
|
|
_.extend(result, data);
|
|
return saveData(collection, result, stopUpdating);
|
|
});
|
|
}
|
|
}
|
|
|
|
|
|
/*
|
|
* options:
|
|
* collection (mandatory)
|
|
* query (mandatory)
|
|
* operation (optional) : version info
|
|
* update (optional) : extends existing content
|
|
*/
|
|
function setMongoContent(data, options, callback) {
|
|
config.debug && config.debug('setMongoContent options', options);
|
|
return db.collection(options.collection, function handleCollection(err, collection) {
|
|
if (err) {
|
|
config.error && config.error('ERR2 setMongoContent', err);
|
|
return callback && callback(err);
|
|
}
|
|
if (options.operation && options.operation.v) {
|
|
data.version = options.operation.v;
|
|
}
|
|
var dumpData = saveData;
|
|
if (options.update) {
|
|
dumpData = updateData;
|
|
}
|
|
if (!data._id) {
|
|
config.debug && config.debug('setMongoContent lookup by query', options.query, 'updating:', options.update);
|
|
collection.findOne(options.query, function foundOne(err, result) {
|
|
if (err) {
|
|
config.error && config.error('ERR3 setMongoContent', err);
|
|
return callback && callback(err);
|
|
}
|
|
if (result && result._id) {
|
|
data._id = result._id;
|
|
}
|
|
return dumpData(collection, data, callback);
|
|
});
|
|
} else {
|
|
return dumpData(collection, data, callback);
|
|
}
|
|
});
|
|
}
|
|
|
|
return {
|
|
saveData: saveData,
|
|
updateData: updateData,
|
|
getAttribute: getMongoAttribute,
|
|
getContent: getMongoContent,
|
|
setContent: setMongoContent
|
|
};
|
|
};
|