mirror of
https://github.com/NodeBB/NodeBB.git
synced 2026-07-13 15:03:17 +02:00
Merge branch 'master' into develop
This commit is contained in:
93
src/groups/data.js
Normal file
93
src/groups/data.js
Normal file
@@ -0,0 +1,93 @@
|
||||
'use strict';
|
||||
|
||||
var async = require('async');
|
||||
var validator = require('validator');
|
||||
|
||||
var db = require('../database');
|
||||
var plugins = require('../plugins');
|
||||
var utils = require('../../public/src/utils');
|
||||
|
||||
module.exports = function (Groups) {
|
||||
Groups.getGroupsData = function (groupNames, callback) {
|
||||
if (!Array.isArray(groupNames) || !groupNames.length) {
|
||||
return callback(null, []);
|
||||
}
|
||||
|
||||
var keys = groupNames.map(function (groupName) {
|
||||
return 'group:' + groupName;
|
||||
});
|
||||
|
||||
var ephemeralIdx = groupNames.reduce(function (memo, cur, idx) {
|
||||
if (Groups.ephemeralGroups.indexOf(cur) !== -1) {
|
||||
memo.push(idx);
|
||||
}
|
||||
return memo;
|
||||
}, []);
|
||||
|
||||
async.waterfall([
|
||||
function (next) {
|
||||
db.getObjects(keys, next);
|
||||
},
|
||||
function (groupData, next) {
|
||||
if (ephemeralIdx.length) {
|
||||
ephemeralIdx.forEach(function (idx) {
|
||||
groupData[idx] = Groups.getEphemeralGroup(groupNames[idx]);
|
||||
});
|
||||
}
|
||||
|
||||
groupData.forEach(function (group) {
|
||||
if (group) {
|
||||
Groups.escapeGroupData(group);
|
||||
group.userTitleEnabled = group.userTitleEnabled ? parseInt(group.userTitleEnabled, 10) === 1 : true;
|
||||
group.labelColor = validator.escape(String(group.labelColor || '#000000'));
|
||||
group.icon = validator.escape(String(group.icon || ''));
|
||||
group.createtimeISO = utils.toISOString(group.createtime);
|
||||
group.hidden = parseInt(group.hidden, 10) === 1;
|
||||
group.system = parseInt(group.system, 10) === 1;
|
||||
group.private = (group.private === null || group.private === undefined) ? true : !!parseInt(group.private, 10);
|
||||
group.disableJoinRequests = parseInt(group.disableJoinRequests, 10) === 1;
|
||||
|
||||
group['cover:url'] = group['cover:url'] || require('../coverPhoto').getDefaultGroupCover(group.name);
|
||||
group['cover:thumb:url'] = group['cover:thumb:url'] || group['cover:url'];
|
||||
group['cover:position'] = validator.escape(String(group['cover:position'] || '50% 50%'));
|
||||
}
|
||||
});
|
||||
|
||||
plugins.fireHook('filter:groups.get', { groups: groupData }, next);
|
||||
},
|
||||
function (results, next) {
|
||||
next(null, results.groups);
|
||||
},
|
||||
], callback);
|
||||
};
|
||||
|
||||
Groups.getGroupData = function (groupName, callback) {
|
||||
Groups.getGroupsData([groupName], function (err, groupsData) {
|
||||
callback(err, Array.isArray(groupsData) && groupsData[0] ? groupsData[0] : null);
|
||||
});
|
||||
};
|
||||
|
||||
Groups.getGroupFields = function (groupName, fields, callback) {
|
||||
Groups.getMultipleGroupFields([groupName], fields, function (err, groups) {
|
||||
callback(err, groups ? groups[0] : null);
|
||||
});
|
||||
};
|
||||
|
||||
Groups.getMultipleGroupFields = function (groups, fields, callback) {
|
||||
db.getObjectsFields(groups.map(function (group) {
|
||||
return 'group:' + group;
|
||||
}), fields, callback);
|
||||
};
|
||||
|
||||
Groups.setGroupField = function (groupName, field, value, callback) {
|
||||
async.waterfall([
|
||||
function (next) {
|
||||
db.setObjectField('group:' + groupName, field, value, next);
|
||||
},
|
||||
function (next) {
|
||||
plugins.fireHook('action:group.set', { field: field, value: value, type: 'set' });
|
||||
next();
|
||||
},
|
||||
], callback);
|
||||
};
|
||||
};
|
||||
@@ -413,32 +413,33 @@ module.exports = function (Groups) {
|
||||
};
|
||||
|
||||
Groups.getMemberCount = function (groupName, callback) {
|
||||
db.getObjectField('group:' + groupName, 'memberCount', function (err, count) {
|
||||
if (err) {
|
||||
return callback(err);
|
||||
}
|
||||
callback(null, parseInt(count, 10));
|
||||
});
|
||||
async.waterfall([
|
||||
function (next) {
|
||||
db.getObjectField('group:' + groupName, 'memberCount', next);
|
||||
},
|
||||
function (count, next) {
|
||||
next(null, parseInt(count, 10));
|
||||
},
|
||||
], callback);
|
||||
};
|
||||
|
||||
Groups.isMemberOfGroupList = function (uid, groupListKey, callback) {
|
||||
db.getSortedSetRange('group:' + groupListKey + ':members', 0, -1, function (err, groupNames) {
|
||||
if (err) {
|
||||
return callback(err);
|
||||
}
|
||||
groupNames = Groups.internals.removeEphemeralGroups(groupNames);
|
||||
if (groupNames.length === 0) {
|
||||
return callback(null, false);
|
||||
}
|
||||
|
||||
Groups.isMemberOfGroups(uid, groupNames, function (err, isMembers) {
|
||||
if (err) {
|
||||
return callback(err);
|
||||
async.waterfall([
|
||||
function (next) {
|
||||
db.getSortedSetRange('group:' + groupListKey + ':members', 0, -1, next);
|
||||
},
|
||||
function (groupNames, next) {
|
||||
groupNames = Groups.removeEphemeralGroups(groupNames);
|
||||
if (groupNames.length === 0) {
|
||||
return callback(null, false);
|
||||
}
|
||||
|
||||
callback(null, isMembers.indexOf(true) !== -1);
|
||||
});
|
||||
});
|
||||
Groups.isMemberOfGroups(uid, groupNames, next);
|
||||
},
|
||||
function (isMembers, next) {
|
||||
next(null, isMembers.indexOf(true) !== -1);
|
||||
},
|
||||
], callback);
|
||||
};
|
||||
|
||||
Groups.isMemberOfGroupsList = function (uid, groupListKeys, callback) {
|
||||
@@ -446,19 +447,20 @@ module.exports = function (Groups) {
|
||||
return 'group:' + groupName + ':members';
|
||||
});
|
||||
|
||||
db.getSortedSetsMembers(sets, function (err, members) {
|
||||
if (err) {
|
||||
return callback(err);
|
||||
}
|
||||
|
||||
var uniqueGroups = _.unique(_.flatten(members));
|
||||
uniqueGroups = Groups.internals.removeEphemeralGroups(uniqueGroups);
|
||||
|
||||
Groups.isMemberOfGroups(uid, uniqueGroups, function (err, isMembers) {
|
||||
if (err) {
|
||||
return callback(err);
|
||||
}
|
||||
var uniqueGroups;
|
||||
var members;
|
||||
async.waterfall([
|
||||
function (next) {
|
||||
db.getSortedSetsMembers(sets, next);
|
||||
},
|
||||
function (_members, next) {
|
||||
members = _members;
|
||||
uniqueGroups = _.unique(_.flatten(members));
|
||||
uniqueGroups = Groups.removeEphemeralGroups(uniqueGroups);
|
||||
|
||||
Groups.isMemberOfGroups(uid, uniqueGroups, next);
|
||||
},
|
||||
function (isMembers, next) {
|
||||
var map = {};
|
||||
|
||||
uniqueGroups.forEach(function (groupName, index) {
|
||||
@@ -474,62 +476,63 @@ module.exports = function (Groups) {
|
||||
return false;
|
||||
});
|
||||
|
||||
callback(null, result);
|
||||
});
|
||||
});
|
||||
next(null, result);
|
||||
},
|
||||
], callback);
|
||||
};
|
||||
|
||||
Groups.isMembersOfGroupList = function (uids, groupListKey, callback) {
|
||||
db.getSortedSetRange('group:' + groupListKey + ':members', 0, -1, function (err, groupNames) {
|
||||
if (err) {
|
||||
return callback(err);
|
||||
}
|
||||
var groupNames;
|
||||
var results = [];
|
||||
uids.forEach(function () {
|
||||
results.push(false);
|
||||
});
|
||||
|
||||
var results = [];
|
||||
uids.forEach(function () {
|
||||
results.push(false);
|
||||
});
|
||||
async.waterfall([
|
||||
function (next) {
|
||||
db.getSortedSetRange('group:' + groupListKey + ':members', 0, -1, next);
|
||||
},
|
||||
function (_groupNames, next) {
|
||||
groupNames = Groups.removeEphemeralGroups(_groupNames);
|
||||
|
||||
groupNames = Groups.internals.removeEphemeralGroups(groupNames);
|
||||
if (groupNames.length === 0) {
|
||||
return callback(null, results);
|
||||
}
|
||||
if (groupNames.length === 0) {
|
||||
return callback(null, results);
|
||||
}
|
||||
|
||||
async.each(groupNames, function (groupName, next) {
|
||||
Groups.isMembers(uids, groupName, function (err, isMembers) {
|
||||
if (err) {
|
||||
return next(err);
|
||||
}
|
||||
async.map(groupNames, function (groupName, next) {
|
||||
Groups.isMembers(uids, groupName, next);
|
||||
}, next);
|
||||
},
|
||||
function (isGroupMembers, next) {
|
||||
isGroupMembers.forEach(function (isMembers) {
|
||||
results.forEach(function (isMember, index) {
|
||||
if (!isMember && isMembers[index]) {
|
||||
results[index] = true;
|
||||
}
|
||||
});
|
||||
next();
|
||||
});
|
||||
}, function (err) {
|
||||
callback(err, results);
|
||||
});
|
||||
});
|
||||
next(null, results);
|
||||
},
|
||||
], callback);
|
||||
};
|
||||
|
||||
Groups.isInvited = function (uid, groupName, callback) {
|
||||
if (!uid) {
|
||||
return callback(null, false);
|
||||
return setImmediate(callback, null, false);
|
||||
}
|
||||
db.isSetMember('group:' + groupName + ':invited', uid, callback);
|
||||
};
|
||||
|
||||
Groups.isPending = function (uid, groupName, callback) {
|
||||
if (!uid) {
|
||||
return callback(null, false);
|
||||
return setImmediate(callback, null, false);
|
||||
}
|
||||
db.isSetMember('group:' + groupName + ':pending', uid, callback);
|
||||
};
|
||||
|
||||
Groups.getPending = function (groupName, callback) {
|
||||
if (!groupName) {
|
||||
return callback(null, []);
|
||||
return setImmediate(callback, null, []);
|
||||
}
|
||||
db.getSetMembers('group:' + groupName + ':pending', callback);
|
||||
};
|
||||
|
||||
32
src/groups/posts.js
Normal file
32
src/groups/posts.js
Normal file
@@ -0,0 +1,32 @@
|
||||
'use strict';
|
||||
|
||||
var async = require('async');
|
||||
|
||||
var db = require('../database');
|
||||
var privileges = require('../privileges');
|
||||
var posts = require('../posts');
|
||||
|
||||
module.exports = function (Groups) {
|
||||
Groups.getLatestMemberPosts = function (groupName, max, uid, callback) {
|
||||
async.waterfall([
|
||||
function (next) {
|
||||
Groups.getMembers(groupName, 0, -1, next);
|
||||
},
|
||||
function (uids, next) {
|
||||
if (!Array.isArray(uids) || !uids.length) {
|
||||
return callback(null, []);
|
||||
}
|
||||
var keys = uids.map(function (uid) {
|
||||
return 'uid:' + uid + ':posts';
|
||||
});
|
||||
db.getSortedSetRevRange(keys, 0, max - 1, next);
|
||||
},
|
||||
function (pids, next) {
|
||||
privileges.posts.filter('read', pids, uid, next);
|
||||
},
|
||||
function (pids, next) {
|
||||
posts.getPostSummaryByPids(pids, uid, { stripTags: false }, next);
|
||||
},
|
||||
], callback);
|
||||
};
|
||||
};
|
||||
@@ -16,7 +16,7 @@ module.exports = function (Groups) {
|
||||
async.apply(db.getObjectValues, 'groupslug:groupname'),
|
||||
function (groupNames, next) {
|
||||
// Ephemeral groups and the registered-users groups are searchable
|
||||
groupNames = Groups.getEphemeralGroups().concat(groupNames).concat('registered-users');
|
||||
groupNames = Groups.ephemeralGroups.concat(groupNames).concat('registered-users');
|
||||
groupNames = groupNames.filter(function (name) {
|
||||
return name.toLowerCase().indexOf(query) !== -1 && name !== 'administrators' && !Groups.isPrivilegeGroup(name);
|
||||
});
|
||||
|
||||
50
src/groups/user.js
Normal file
50
src/groups/user.js
Normal file
@@ -0,0 +1,50 @@
|
||||
'use strict';
|
||||
|
||||
var async = require('async');
|
||||
|
||||
var db = require('../database');
|
||||
var user = require('../user');
|
||||
|
||||
module.exports = function (Groups) {
|
||||
Groups.getUsersFromSet = function (set, callback) {
|
||||
async.waterfall([
|
||||
function (next) {
|
||||
db.getSetMembers(set, next);
|
||||
},
|
||||
function (uids, next) {
|
||||
user.getUsersData(uids, next);
|
||||
},
|
||||
], callback);
|
||||
};
|
||||
|
||||
Groups.getUserGroups = function (uids, callback) {
|
||||
Groups.getUserGroupsFromSet('groups:visible:createtime', uids, callback);
|
||||
};
|
||||
|
||||
Groups.getUserGroupsFromSet = function (set, uids, callback) {
|
||||
async.waterfall([
|
||||
function (next) {
|
||||
db.getSortedSetRevRange(set, 0, -1, next);
|
||||
},
|
||||
function (groupNames, next) {
|
||||
async.map(uids, function (uid, next) {
|
||||
async.waterfall([
|
||||
function (next) {
|
||||
Groups.isMemberOfGroups(uid, groupNames, next);
|
||||
},
|
||||
function (isMembers, next) {
|
||||
var memberOf = [];
|
||||
isMembers.forEach(function (isMember, index) {
|
||||
if (isMember) {
|
||||
memberOf.push(groupNames[index]);
|
||||
}
|
||||
});
|
||||
|
||||
Groups.getGroupsData(memberOf, next);
|
||||
},
|
||||
], next);
|
||||
}, next);
|
||||
},
|
||||
], callback);
|
||||
};
|
||||
};
|
||||
Reference in New Issue
Block a user