landmark-serve
Version:
Web Application Framework and Admin GUI / Content Management System built on Express.js and Mongoose
260 lines (193 loc) • 6.04 kB
JavaScript
var _ = require('underscore'),
async = require('async'),
landmark = require('../../'),
jade = require('jade');;
exports = module.exports = function(req, res) {
var sendResponse = function(status) {
res.json(status);
};
var sendError = function(key, err, msg) {
msg = msg || 'API Error';
key = key || 'unknown error';
msg += ' (' + key + ')';
console.log(msg + (err ? ':' : ''));
if (err) {
console.log(err);
}
res.status(500);
sendResponse({ error: key || 'error', detail: err });
};
switch (req.params.action) {
case 'autocomplete':
var limit = req.query.limit || 10,
page = req.query.page || 1,
skip = limit * (page - 1);
var filters = req.list.getSearchFilters(req.query.q);
var count = req.list.model.count(filters),
query = req.list.model.find(filters)
.limit(limit)
.skip(skip)
.sort(req.list.defaultSort);
var doQuery = function() {
count.exec(function(err, total) {
if (err) return sendError('database error', err);
query.exec(function(err, items) {
if (err) return sendError('database error', err);
sendResponse({
total: total,
items: items.map(function(i) {
return {
name: req.list.getDocumentName(i, true) || '(' + i.id + ')',
id: i.id
};
})
});
});
});
};
if (req.query.context === 'relationship') {
var srcList = landmark.list(req.query.list);
if (!srcList) return sendError('invalid list provided');
var field = srcList.fields[req.query.field];
if (!field || field.type !== 'relationship') return sendError('invalid field provided');
if (!field.hasFilters) {
return doQuery();
}
_.each(req.query.filters, function(value, key) {
query.where(key).equals(value ? value : null);
count.where(key).equals(value ? value : null);
});
return doQuery();
} else {
return doQuery();
}
break;
case 'get':
req.list.model.findById(req.query.id).exec(function(err, item) {
if (err) return sendError('database error', err);
if (!item) return sendResponse({ name: req.query.id, id: req.query.id });
switch (req.query.dataset) {
case 'simple':
return sendResponse({
name: req.list.getDocumentName(item, true),
id: item.id
});
default:
return sendResponse(item);
}
});
break;
case 'order':
if (!landmark.security.csrf.validate(req)) {
return sendError('invalid csrf');
}
var order = req.query.order || req.body.order,
queue = [];
if ('string' === typeof order) {
order = order.split(',');
}
_.each(order, function(id, i) {
queue.push(function(done) {
req.list.model.update({ _id: id }, { $set: { sortOrder: i }}, done);
});
});
async.parallel(queue, function(err) {
if (err) return sendError('database error', err);
return sendResponse({
success: true
});
});
break;
case 'create':
if (!landmark.security.csrf.validate(req)) {
return sendError('invalid csrf');
}
var item = new req.list.model(),
updateHandler = item.getUpdateHandler(req),
data = (req.method === 'POST') ? req.body : req.query;
if (req.list.nameIsInitial) {
if (req.list.nameField.validateInput(data)) {
req.list.nameField.updateItem(item, data);
} else {
updateHandler.addValidationError(req.list.nameField.path, 'Name is required.');
}
}
updateHandler.process(data, {
flashErrors: true,
logErrors: true,
fields: req.list.initialFields
}, function(err) {
if (err) {
return sendResponse({
success: false,
err: err
});
} else {
return sendResponse({
success: true,
name: req.list.getDocumentName(item, true),
id: item.id
});
}
});
break;
case 'delete':
if (!landmark.security.csrf.validate(req)) {
return sendError('invalid csrf');
}
if (req.list.get('nodelete')) {
return sendError('nodelete');
}
var id = req.body.id || req.query.id;
req.list.model.findById(id).exec(function (err, item) {
if (err) return sendError('database error', err);
if (!item) return sendError('not found');
item.remove(function (err) {
if (err) return sendError('database error', err);
return sendResponse({
success: true,
count: 1
});
});
});
break;
case 'fetch':
if (!landmark.security.csrf.validate(req)) {
return sendError('invalid csrf');
}
var queryFilters = req.list.getSearchFilters(req.query.search, req.query.filters),
skip = parseInt(req.query.items.last) - 1,
querystring = require('querystring'),
link_to = function(params) {
var p = params.page || '';
delete params.page;
var queryParams = _.clone(req.query.q);
for (var i in params) {
if (params[i] === undefined) {
delete params[i];
delete queryParams[i];
}
}
params = querystring.stringify(_.defaults(params, queryParams));
return '/landmark/' + req.list.path + (p ? '/' + p : '') + (params ? '?' + params : '');
};
req.list.model.find(queryFilters).sort(req.query.sort).skip(skip).limit(1).exec(function(err, items) {
if (err) return sendError('database error', err);
if (!items) return sendError('not found');
var locals, row, pagination;
req.list.expandColumns(req.query.cols);
req.list.getPages(req.query.items, req.list.pagination.maxPages);
locals = { list: req.list, columns: req.list.expandColumns(req.query.cols), item: items[0], csrf_query: req.query.csrf_query };
row = jade.renderFile(__dirname + '/../../templates/partials/row.jade', locals);
pagination = jade.renderFile(__dirname + '/../../templates/partials/pagination.jade', {items: req.query.items, link_to: link_to });
return sendResponse({
item: items[0],
row: row,
pagination: pagination,
success: true,
count: 1
});
});
break;
}
};