Update files

This commit is contained in:
glpshchn 2025-12-07 06:08:07 +03:00
parent ed08ca5140
commit aeae68b39e
4 changed files with 175 additions and 0 deletions

View File

@ -354,6 +354,10 @@ router.delete('/posts/:id', authenticateModeration, requireModerationAccess, asy
console.error('❌ Ошибка удаления файлов из MinIO:', error);
}
// Списать все билеты, связанные с удаленным постом (только если пост создан сегодня)
const { deductPostDeletion } = require('../utils/tickets');
await deductPostDeletion(post);
await Post.deleteOne({ _id: post._id });
res.json({ success: true });
});

View File

@ -84,6 +84,12 @@ router.put('/reports/:id', authenticate, requireModerator, async (req, res) => {
// Выполнить действие
if (action === 'delete_post' && report.post) {
const post = await Post.findById(report.post._id);
if (post) {
// Списать все билеты, связанные с удаленным постом (только если пост создан сегодня)
const { deductPostDeletion } = require('../utils/tickets');
await deductPostDeletion(post);
}
await Post.findByIdAndDelete(report.post._id);
report.status = 'resolved';
} else if (action === 'ban_user' && report.post) {

View File

@ -391,6 +391,10 @@ router.delete('/:id', authenticate, async (req, res) => {
// Продолжаем удаление поста даже если файлы не удалились
}
// Списать все билеты, связанные с удаленным постом (только если пост создан сегодня)
const { deductPostDeletion } = require('../utils/tickets');
await deductPostDeletion(post);
await Post.findByIdAndDelete(req.params.id);
res.json({ message: 'Пост удален' });
} catch (error) {

View File

@ -205,6 +205,164 @@ async function awardArtComment(authorId, commenterId, postId) {
});
}
/**
* Списывает билеты за действие (лайк/комментарий) с удаленным постом
*/
async function deductAction(userId, points, actionType, postCreatedAt) {
try {
const { getMoscowStartOfDay } = require('./moscowTime');
// Проверяем, что действие было в день создания поста
const postDate = getMoscowStartOfDay(postCreatedAt);
const today = getMoscowStartOfDay();
// Если пост создан не сегодня, не списываем билеты
if (postDate.getTime() !== today.getTime()) {
return { success: false, reason: 'post_not_today' };
}
// Получить активность за сегодня
const activity = await TicketActivity.getOrCreateToday(userId);
// Уменьшить счетчики активности
switch (actionType) {
case 'post_created':
if (activity.postsCreated > 0) {
activity.postsCreated -= 1;
}
break;
case 'like_given':
if (activity.likesGiven > 0) {
activity.likesGiven -= 1;
}
break;
case 'like_received':
if (activity.likesReceived > 0) {
activity.likesReceived -= 1;
}
break;
case 'comment_written':
if (activity.commentsWritten > 0) {
activity.commentsWritten -= 1;
}
break;
case 'comment_received':
if (activity.commentsReceived > 0) {
activity.commentsReceived -= 1;
}
break;
}
await activity.save();
// Списать билеты (но не меньше 0)
const user = await User.findById(userId);
if (user) {
const ticketsToDeduct = Math.min(points, user.tickets || 0);
if (ticketsToDeduct > 0) {
await User.findByIdAndUpdate(userId, {
$inc: { tickets: -ticketsToDeduct }
});
console.log(`[Tickets ${formatMoscowTime()}] Списано ${ticketsToDeduct} билетов пользователю ${userId} за ${actionType}`);
return { success: true, points: -ticketsToDeduct };
}
}
return { success: true, points: 0 };
} catch (error) {
console.error(`[Tickets] Ошибка списания билетов за действие:`, error);
return { success: false, reason: 'error', error: error.message };
}
}
/**
* Списывает все билеты, связанные с удаленным постом
* Списывает только действия, которые были в день создания поста
*/
async function deductPostDeletion(post) {
try {
const { getMoscowStartOfDay } = require('./moscowTime');
// Проверяем, что пост был создан сегодня
const postDate = getMoscowStartOfDay(post.createdAt);
const today = getMoscowStartOfDay();
// Если пост создан не сегодня, не списываем билеты
if (postDate.getTime() !== today.getTime()) {
console.log(`[Tickets ${formatMoscowTime()}] Пост создан не сегодня, билеты не списываются`);
return { success: false, reason: 'post_not_today' };
}
const authorId = post.author;
const postCreatedAt = post.createdAt;
// 1. Списываем билеты за создание поста у автора
await deductAction(authorId, 15, 'post_created', postCreatedAt);
// 2. Списываем билеты за полученные лайки у автора
if (post.likes && post.likes.length > 0) {
for (const likerId of post.likes) {
// Проверяем, что лайк был поставлен в день создания поста
// (лайки не имеют даты, но если пост создан сегодня, то и лайки сегодня)
await deductAction(authorId, 2, 'like_received', postCreatedAt);
}
}
// 3. Списываем билеты за полученные комментарии у автора
if (post.comments && post.comments.length > 0) {
for (const comment of post.comments) {
// Проверяем, что комментарий был написан в день создания поста
const commentDate = getMoscowStartOfDay(comment.createdAt || comment.created_at || postCreatedAt);
if (commentDate.getTime() === postDate.getTime()) {
await deductAction(authorId, 6, 'comment_received', postCreatedAt);
}
}
}
// 4. Списываем билеты у тех, кто поставил лайк (за поставленный лайк)
if (post.likes && post.likes.length > 0) {
for (const likerId of post.likes) {
// Проверяем, что это не автор поста
if (!likerId.equals(authorId)) {
await deductAction(likerId, 1, 'like_given', postCreatedAt);
}
}
}
// 5. Списываем билеты у тех, кто написал комментарий (за написанный комментарий)
if (post.comments && post.comments.length > 0) {
for (const comment of post.comments) {
const commentAuthorId = comment.author;
if (commentAuthorId && !commentAuthorId.equals(authorId)) {
// Проверяем, что комментарий был написан в день создания поста
const commentDate = getMoscowStartOfDay(comment.createdAt || comment.created_at || postCreatedAt);
if (commentDate.getTime() === postDate.getTime()) {
// Проверяем длину комментария (>= 10 символов для начисления)
const commentLength = (comment.content || '').trim().length;
if (commentLength >= 10) {
await deductAction(commentAuthorId, 4, 'comment_written', postCreatedAt);
}
}
}
}
}
console.log(`[Tickets ${formatMoscowTime()}] Списаны все билеты за удаление поста ${post._id}`);
return { success: true };
} catch (error) {
console.error(`[Tickets] Ошибка списания билетов за удаление поста:`, error);
return { success: false, reason: 'error', error: error.message };
}
}
/**
* Списывает билеты при удалении поста (старая функция для обратной совместимости)
* @deprecated Используйте deductPostDeletion вместо этого
*/
async function deductPostCreation(userId, postCreatedAt) {
return await deductAction(userId, 15, 'post_created', postCreatedAt);
}
module.exports = {
awardTickets,
awardPostCreation,
@ -215,6 +373,9 @@ module.exports = {
awardReferral,
awardArtLike,
awardArtComment,
deductPostCreation,
deductPostDeletion,
deductAction,
canAwardTickets,
isAccountOldEnough
};