You cannot select more than 25 topics
Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
138 lines
4.2 KiB
JavaScript
138 lines
4.2 KiB
JavaScript
'use strict';
|
|
|
|
const db = require('../database');
|
|
|
|
const user = require('../user');
|
|
const posts = require('../posts');
|
|
const categories = require('../categories');
|
|
const plugins = require('../plugins');
|
|
const batch = require('../batch');
|
|
|
|
|
|
module.exports = function (Topics) {
|
|
Topics.delete = async function (tid, uid) {
|
|
const cid = await Topics.getTopicField(tid, 'cid');
|
|
await removeTopicPidsFromCid(tid, cid);
|
|
await Topics.setTopicFields(tid, {
|
|
deleted: 1,
|
|
deleterUid: uid,
|
|
deletedTimestamp: Date.now(),
|
|
});
|
|
await categories.updateRecentTidForCid(cid);
|
|
};
|
|
|
|
async function removeTopicPidsFromCid(tid, cid) {
|
|
const pids = await Topics.getPids(tid);
|
|
await db.sortedSetRemove(`cid:${cid}:pids`, pids);
|
|
}
|
|
|
|
async function addTopicPidsToCid(tid, cid) {
|
|
const pids = await Topics.getPids(tid);
|
|
let postData = await posts.getPostsFields(pids, ['pid', 'timestamp', 'deleted']);
|
|
postData = postData.filter(post => post && !post.deleted);
|
|
const pidsToAdd = postData.map(post => post.pid);
|
|
const scores = postData.map(post => post.timestamp);
|
|
await db.sortedSetAdd(`cid:${cid}:pids`, scores, pidsToAdd);
|
|
}
|
|
|
|
Topics.restore = async function (tid) {
|
|
const cid = await Topics.getTopicField(tid, 'cid');
|
|
await Promise.all([
|
|
Topics.deleteTopicFields(tid, [
|
|
'deleterUid', 'deletedTimestamp',
|
|
]),
|
|
addTopicPidsToCid(tid, cid),
|
|
]);
|
|
await Topics.setTopicField(tid, 'deleted', 0);
|
|
await categories.updateRecentTidForCid(cid);
|
|
};
|
|
|
|
Topics.purgePostsAndTopic = async function (tid, uid) {
|
|
const mainPid = await Topics.getTopicField(tid, 'mainPid');
|
|
await batch.processSortedSet(`tid:${tid}:posts`, async (pids) => {
|
|
await posts.purge(pids, uid);
|
|
}, { alwaysStartAt: 0, batch: 500 });
|
|
await posts.purge(mainPid, uid);
|
|
await Topics.purge(tid, uid);
|
|
};
|
|
|
|
Topics.purge = async function (tid, uid) {
|
|
const [deletedTopic, tags] = await Promise.all([
|
|
Topics.getTopicData(tid),
|
|
Topics.getTopicTags(tid),
|
|
]);
|
|
if (!deletedTopic) {
|
|
return;
|
|
}
|
|
deletedTopic.tags = tags;
|
|
await deleteFromFollowersIgnorers(tid);
|
|
|
|
await Promise.all([
|
|
db.deleteAll([
|
|
`tid:${tid}:followers`,
|
|
`tid:${tid}:ignorers`,
|
|
`tid:${tid}:posts`,
|
|
`tid:${tid}:posts:votes`,
|
|
`tid:${tid}:bookmarks`,
|
|
`tid:${tid}:posters`,
|
|
]),
|
|
db.sortedSetsRemove([
|
|
'topics:tid',
|
|
'topics:recent',
|
|
'topics:posts',
|
|
'topics:views',
|
|
'topics:votes',
|
|
'topics:scheduled',
|
|
], tid),
|
|
deleteTopicFromCategoryAndUser(tid),
|
|
Topics.deleteTopicTags(tid),
|
|
Topics.events.purge(tid),
|
|
Topics.thumbs.deleteAll(tid),
|
|
reduceCounters(tid),
|
|
]);
|
|
plugins.hooks.fire('action:topic.purge', { topic: deletedTopic, uid: uid });
|
|
await db.delete(`topic:${tid}`);
|
|
};
|
|
|
|
async function deleteFromFollowersIgnorers(tid) {
|
|
const [followers, ignorers] = await Promise.all([
|
|
db.getSetMembers(`tid:${tid}:followers`),
|
|
db.getSetMembers(`tid:${tid}:ignorers`),
|
|
]);
|
|
const followerKeys = followers.map(uid => `uid:${uid}:followed_tids`);
|
|
const ignorerKeys = ignorers.map(uid => `uid:${uid}ignored_tids`);
|
|
await db.sortedSetsRemove(followerKeys.concat(ignorerKeys), tid);
|
|
}
|
|
|
|
async function deleteTopicFromCategoryAndUser(tid) {
|
|
const topicData = await Topics.getTopicFields(tid, ['cid', 'uid']);
|
|
await Promise.all([
|
|
db.sortedSetsRemove([
|
|
`cid:${topicData.cid}:tids`,
|
|
`cid:${topicData.cid}:tids:pinned`,
|
|
`cid:${topicData.cid}:tids:posts`,
|
|
`cid:${topicData.cid}:tids:lastposttime`,
|
|
`cid:${topicData.cid}:tids:votes`,
|
|
`cid:${topicData.cid}:tids:views`,
|
|
`cid:${topicData.cid}:recent_tids`,
|
|
`cid:${topicData.cid}:uid:${topicData.uid}:tids`,
|
|
`uid:${topicData.uid}:topics`,
|
|
], tid),
|
|
user.decrementUserFieldBy(topicData.uid, 'topiccount', 1),
|
|
]);
|
|
await categories.updateRecentTidForCid(topicData.cid);
|
|
}
|
|
|
|
async function reduceCounters(tid) {
|
|
const incr = -1;
|
|
await db.incrObjectFieldBy('global', 'topicCount', incr);
|
|
const topicData = await Topics.getTopicFields(tid, ['cid', 'postcount']);
|
|
const postCountChange = incr * topicData.postcount;
|
|
await Promise.all([
|
|
db.incrObjectFieldBy('global', 'postCount', postCountChange),
|
|
db.incrObjectFieldBy(`category:${topicData.cid}`, 'post_count', postCountChange),
|
|
db.incrObjectFieldBy(`category:${topicData.cid}`, 'topic_count', incr),
|
|
]);
|
|
}
|
|
};
|