diff --git a/src/controllers/api.js b/src/controllers/api.js index fb5ab709b6..77ae7131ad 100644 --- a/src/controllers/api.js +++ b/src/controllers/api.js @@ -1,32 +1,21 @@ "use strict"; -var async = require('async'), - validator = require('validator'), - nconf = require('nconf'), - - meta = require('../meta'), - user = require('../user'), - posts = require('../posts'), - topics = require('../topics'), - categories = require('../categories'), - privileges = require('../privileges'), - plugins = require('../plugins'), - helpers = require('./helpers'), - widgets = require('../widgets'); +var async = require('async'); +var validator = require('validator'); +var nconf = require('nconf'); + +var meta = require('../meta'); +var user = require('../user'); +var posts = require('../posts'); +var topics = require('../topics'); +var categories = require('../categories'); +var privileges = require('../privileges'); +var plugins = require('../plugins'); +var widgets = require('../widgets'); var apiController = {}; apiController.getConfig = function(req, res, next) { - function filterConfig() { - plugins.fireHook('filter:config.get', config, function(err, config) { - if (res.locals.isAPI) { - res.status(200).json(config); - } else { - next(err, config); - } - }); - } - var config = {}; config.environment = process.env.NODE_ENV; config.relative_path = nconf.get('relative_path'); @@ -51,7 +40,6 @@ apiController.getConfig = function(req, res, next) { config.allowFileUploads = parseInt(meta.config.allowFileUploads, 10) === 1; config.allowTopicsThumbnail = parseInt(meta.config.allowTopicsThumbnail, 10) === 1; config.usePagination = parseInt(meta.config.usePagination, 10) === 1; - config.disableSocialButtons = parseInt(meta.config.disableSocialButtons, 10) === 1; config.disableChat = parseInt(meta.config.disableChat, 10) === 1; config.socketioTransports = nconf.get('socket.io:transports') || ['polling', 'websocket']; config.websocketAddress = nconf.get('socket.io:address') || ''; @@ -73,27 +61,41 @@ apiController.getConfig = function(req, res, next) { config.searchEnabled = plugins.hasListeners('filter:search.query'); config.bootswatchSkin = 'default'; - if (!req.user) { - return filterConfig(); - } - - user.getSettings(req.user.uid, function(err, settings) { + async.waterfall([ + function (next) { + if (!req.user) { + return next(null, config); + } + user.getSettings(req.uid, function(err, settings) { + if (err) { + return next(err); + } + config.usePagination = settings.usePagination; + config.topicsPerPage = settings.topicsPerPage; + config.postsPerPage = settings.postsPerPage; + config.notificationSounds = settings.notificationSounds; + config.userLang = req.query.lang || settings.userLang || config.defaultLang; + config.openOutgoingLinksInNewTab = settings.openOutgoingLinksInNewTab; + config.topicPostSort = settings.topicPostSort || config.topicPostSort; + config.categoryTopicSort = settings.categoryTopicSort || config.categoryTopicSort; + config.topicSearchEnabled = settings.topicSearchEnabled || false; + config.bootswatchSkin = settings.bootswatchSkin || config.bootswatchSkin; + next(null, config); + }); + }, + function (config, next) { + plugins.fireHook('filter:config.get', config, next); + } + ], function(err, config) { if (err) { return next(err); } - config.usePagination = settings.usePagination; - config.topicsPerPage = settings.topicsPerPage; - config.postsPerPage = settings.postsPerPage; - config.notificationSounds = settings.notificationSounds; - config.userLang = req.query.lang || settings.userLang || config.defaultLang; - config.openOutgoingLinksInNewTab = settings.openOutgoingLinksInNewTab; - config.topicPostSort = settings.topicPostSort || config.topicPostSort; - config.categoryTopicSort = settings.categoryTopicSort || config.categoryTopicSort; - config.topicSearchEnabled = settings.topicSearchEnabled || false; - config.bootswatchSkin = settings.bootswatchSkin || config.bootswatchSkin; - - filterConfig(); + if (res.locals.isAPI) { + res.json(config); + } else { + next(null, config); + } }); }; @@ -126,6 +128,16 @@ apiController.renderWidgets = function(req, res, next) { }; apiController.getObject = function(req, res, next) { + apiController.getObjectByType(req.uid, req.params.type, req.params.id, function(err, results) { + if (err) { + return next(err); + } + + res.json(results); + }); +}; + +apiController.getObjectByType = function(uid, type, id, callback) { var methods = { post: { canRead: privileges.posts.can, @@ -141,74 +153,101 @@ apiController.getObject = function(req, res, next) { } }; - if (!methods[req.params.type]) { - return next(); + if (!methods[type]) { + return callback(); } - async.parallel({ - canRead: async.apply(methods[req.params.type].canRead, 'read', req.params.id, req.uid), - data: async.apply(methods[req.params.type].data, req.params.id) - }, function(err, results) { - if (err || !results.data) { - return next(err); - } - - if (!results.canRead) { - return helpers.notAllowed(req, res); + async.waterfall([ + function (next) { + methods[type].canRead('read', id, uid, next); + }, + function (canRead, next) { + if (!canRead) { + return next(new Error('[[error:no-privileges]]')); + } + methods[type].data(id, next); } - - res.json(results.data); - }); + ], callback); }; - apiController.getUserByUID = function(req, res, next) { var uid = req.params.uid ? req.params.uid : 0; - getUserByUID(uid, res, next); + apiController.getUserDataByUID(req.uid, uid, function(err, data) { + if (err) { + return next(err); + } + res.json(data); + }); }; apiController.getUserByUsername = function(req, res, next) { var username = req.params.username ? req.params.username : 0; + apiController.getUserDataByUsername(req.uid, username, function(err, data) { + if (err) { + return next(err); + } + res.json(data); + }); +}; + +apiController.getUserByEmail = function(req, res, next) { + var email = req.params.email ? req.params.email : 0; + + apiController.getUserDataByEmail(req.uid, email, function(err, data) { + if (err) { + return next(err); + } + res.json(data); + }); +}; + +apiController.getUserDataByUsername = function(callerUid, username, callback) { async.waterfall([ function(next) { user.getUidByUsername(username, next); }, function(uid, next) { - getUserByUID(uid, res, next); + apiController.getUserDataByUID(callerUid, uid, next); } - ], next); + ], callback); }; -apiController.getUserByEmail = function(req, res, next) { - var email = req.params.email ? req.params.email : 0; - +apiController.getUserDataByEmail = function(callerUid, email, callback) { async.waterfall([ function(next) { user.getUidByEmail(email, next); }, function(uid, next) { - getUserByUID(uid, res, next); + apiController.getUserDataByUID(callerUid, uid, next); } - ], next); + ], callback); }; -function getUserByUID(uid, res, next) { +apiController.getUserDataByUID = function(callerUid, uid, callback) { + if (!parseInt(callerUid, 10) && parseInt(meta.config.privateUserInfo, 10) === 1) { + return callback(new Error('[[error:no-privileges]]')); + } + + if (!parseInt(uid, 10)) { + return callback(new Error('[[error:no-user]]')); + } + async.parallel({ userData: async.apply(user.getUserData, uid), settings: async.apply(user.getSettings, uid) }, function(err, results) { if (err || !results.userData) { - return next(err); + return callback(err || new Error('[[error:no-user]]')); } results.userData.email = results.settings.showemail ? results.userData.email : undefined; results.userData.fullname = results.settings.showfullname ? results.userData.fullname : undefined; - res.json(results.userData); + callback(null, results.userData); }); -} +}; apiController.getModerators = function(req, res, next) { categories.getModerators(req.params.cid, function(err, moderators) { diff --git a/src/socket.io/categories.js b/src/socket.io/categories.js index 7e8b6000f3..262a5e8a41 100644 --- a/src/socket.io/categories.js +++ b/src/socket.io/categories.js @@ -6,7 +6,7 @@ var categories = require('../categories'); var privileges = require('../privileges'); var user = require('../user'); var topics = require('../topics'); - +var apiController = require('../controllers/api'); var SocketCategories = {}; @@ -192,4 +192,8 @@ SocketCategories.isModerator = function(socket, cid, callback) { user.isModerator(socket.uid, cid, callback); }; +SocketCategories.getCategory = function(socket, cid, callback) { + apiController.getObjectByType(socket.uid, 'category', cid, callback); +}; + module.exports = SocketCategories; diff --git a/src/socket.io/posts.js b/src/socket.io/posts.js index 64b5b75076..b0384820ea 100644 --- a/src/socket.io/posts.js +++ b/src/socket.io/posts.js @@ -1,18 +1,20 @@ "use strict"; -var async = require('async'), +var async = require('async'); - posts = require('../posts'), - privileges = require('../privileges'), - meta = require('../meta'), - topics = require('../topics'), - user = require('../user'), - websockets = require('./index'), - socketTopics = require('./topics'), - socketHelpers = require('./helpers'), - utils = require('../../public/src/utils'), +var posts = require('../posts'); +var privileges = require('../privileges'); +var meta = require('../meta'); +var topics = require('../topics'); +var user = require('../user'); +var websockets = require('./index'); +var socketTopics = require('./topics'); +var socketHelpers = require('./helpers'); +var utils = require('../../public/src/utils'); - SocketPosts = {}; +var apiController = require('../controllers/api'); + +var SocketPosts = {}; require('./posts/edit')(SocketPosts); @@ -77,6 +79,20 @@ SocketPosts.getRawPost = function(socket, pid, callback) { ], callback); }; +SocketPosts.getPost = function(socket, pid, callback) { + async.waterfall([ + function(next) { + apiController.getObjectByType(socket.uid, 'post', pid, next); + }, + function(postData, next) { + if (parseInt(postData.deleted, 10) === 1) { + return next(new Error('[[error:no-post]]')); + } + next(null, postData); + } + ], callback); +}; + SocketPosts.loadMoreFavourites = function(socket, data, callback) { loadMorePosts('uid:' + data.uid + ':favourites', socket.uid, data, callback); }; @@ -119,4 +135,6 @@ SocketPosts.getPidIndex = function(socket, data, callback) { posts.getPidIndex(data.pid, data.tid, data.topicPostSort, callback); }; + + module.exports = SocketPosts; diff --git a/src/socket.io/topics.js b/src/socket.io/topics.js index 940ed0a470..72e6e7c510 100644 --- a/src/socket.io/topics.js +++ b/src/socket.io/topics.js @@ -1,18 +1,17 @@ 'use strict'; -var nconf = require('nconf'), - async = require('async'), - winston = require('winston'), +var async = require('async'); +var winston = require('winston'); - topics = require('../topics'), - privileges = require('../privileges'), - plugins = require('../plugins'), - notifications = require('../notifications'), - websockets = require('./index'), - user = require('../user'), +var topics = require('../topics'); +var privileges = require('../privileges'); +var plugins = require('../plugins'); +var websockets = require('./index'); +var user = require('../user'); +var apiController = require('../controllers/api'); - SocketTopics = {}; +var SocketTopics = {}; require('./topics/unread')(SocketTopics); require('./topics/move')(SocketTopics); @@ -126,4 +125,18 @@ SocketTopics.isModerator = function(socket, tid, callback) { }); }; +SocketTopics.getTopic = function (socket, tid, callback) { + async.waterfall([ + function (next) { + apiController.getObjectByType(socket.uid, 'topic', tid, next); + }, + function (topicData, next) { + if (parseInt(topicData.deleted, 10) === 1) { + return next(new Error('[[error:no-topic]]')); + } + next(null, topicData); + } + ], callback); +}; + module.exports = SocketTopics; diff --git a/src/socket.io/user.js b/src/socket.io/user.js index be884d4c54..ed6caae39e 100644 --- a/src/socket.io/user.js +++ b/src/socket.io/user.js @@ -12,6 +12,7 @@ var meta = require('../meta'); var events = require('../events'); var emailer = require('../emailer'); var db = require('../database'); +var apiController = require('../controllers/api'); var SocketUser = {}; @@ -194,7 +195,7 @@ SocketUser.saveSettings = function(socket, data, callback) { return next(null, true); } user.isAdminOrGlobalMod(socket.uid, next); - }, + }, function(allowed, next) { if (!allowed) { return next(new Error('[[error:no-privileges]]')); @@ -332,5 +333,17 @@ SocketUser.invite = function(socket, email, callback) { }; +SocketUser.getUserByUID = function(socket, uid, callback) { + apiController.getUserDataByUID(socket.uid, uid, callback); +}; + +SocketUser.getUserByUsername = function(socket, username, callback) { + apiController.getUserDataByUsername(socket.uid, username, callback); +}; + +SocketUser.getUserByEmail = function(socket, email, callback) { + apiController.getUserDataByEmail(socket.uid, email, callback); +}; + module.exports = SocketUser;