From dabd4667193fe6da662832cc9d52e2f7ef96bae9 Mon Sep 17 00:00:00 2001 From: Kalista Payne Date: Wed, 10 Dec 2025 14:16:48 -0600 Subject: [PATCH] Revert "Chat optimization (#15545)" This reverts commit 2917955ef044c8dd044b41f36b6f561d2dd7c408. --- .../inbox/GET-inbox_messages.test.js | 2 +- .../v4/inbox/GET-inbox-conversations.test.js | 2 +- website/client/src/components/appFooter.vue | 54 ----------- .../src/pages/private-messages/index.vue | 2 +- website/client/src/store/actions/chat.js | 2 +- website/server/controllers/api-v3/chat.js | 7 +- website/server/controllers/api-v3/debug.js | 91 ------------------- website/server/libs/chat/group-chat.js | 21 +---- website/server/libs/inbox/index.js | 18 +--- website/server/models/group.js | 4 +- 10 files changed, 17 insertions(+), 186 deletions(-) diff --git a/test/api/v3/integration/inbox/GET-inbox_messages.test.js b/test/api/v3/integration/inbox/GET-inbox_messages.test.js index 85b223bcab..e3436a3cc4 100644 --- a/test/api/v3/integration/inbox/GET-inbox_messages.test.js +++ b/test/api/v3/integration/inbox/GET-inbox_messages.test.js @@ -47,7 +47,7 @@ describe('GET /inbox/messages', () => { it('returns four messages when using page-query ', async () => { const promises = []; - for (let i = 0; i < 50; i += 1) { + for (let i = 0; i < 10; i += 1) { promises.push(user.post('/members/send-private-message', { toUserId: user.id, message: 'fourth', diff --git a/test/api/v4/inbox/GET-inbox-conversations.test.js b/test/api/v4/inbox/GET-inbox-conversations.test.js index 2803bd0fbb..1ee66dda51 100644 --- a/test/api/v4/inbox/GET-inbox-conversations.test.js +++ b/test/api/v4/inbox/GET-inbox-conversations.test.js @@ -66,7 +66,7 @@ describe('GET /inbox/conversations', () => { it('returns five messages when using page-query ', async () => { const promises = []; - for (let i = 0; i < 50; i += 1) { + for (let i = 0; i < 10; i += 1) { promises.push(user.post('/members/send-private-message', { toUserId: user.id, message: 'fourth', diff --git a/website/client/src/components/appFooter.vue b/website/client/src/components/appFooter.vue index 0eae4cbf8f..39d02c94a8 100644 --- a/website/client/src/components/appFooter.vue +++ b/website/client/src/components/appFooter.vue @@ -396,32 +396,6 @@ class="btn btn-secondary" @click="makeAdmin()" >Make Admin -
- - Send Party Chat Messages -
-
- - Send Inbox Messages -
@@ -912,8 +886,6 @@ export default { DEBUG_ENABLED, TIME_TRAVEL_ENABLED, lastTimeJump: null, - partyChatCount: 450, - inboxCount: 450, }; }, computed: { @@ -1032,32 +1004,6 @@ export default { // Reload the website then go to Help > Admin Panel to set contributor level, etc.'); // @TODO: sync() }, - async seedPartyChat () { - try { - const count = this.partyChatCount; - if (!Number.isInteger(count) || count < 1) { - window.alert('Please enter a positive integer'); // eslint-disable-line no-alert - return; - } - await axios.post('/api/v4/debug/seed-party-chat', { messageCount: count }); - window.alert(`Successfully sent ${count} messages to your party chat!`); // eslint-disable-line no-alert - } catch (e) { - window.alert(e.response?.data?.message || 'Error sending party chat messages'); // eslint-disable-line no-alert - } - }, - async seedInbox () { - try { - const count = this.inboxCount; - if (!Number.isInteger(count) || count < 1) { - window.alert('Please enter a positive integer'); // eslint-disable-line no-alert - return; - } - await axios.post('/api/v4/debug/seed-inbox', { messageCount: count }); - window.alert(`Successfully sent ${count} messages to your inbox!`); // eslint-disable-line no-alert - } catch (e) { - window.alert(e.response?.data?.message || 'Error sending inbox messages'); // eslint-disable-line no-alert - } - }, donate () { this.$root.$emit('bv::show::modal', 'buy-gems', { alreadyTracked: true }); }, diff --git a/website/client/src/pages/private-messages/index.vue b/website/client/src/pages/private-messages/index.vue index 4e347ce870..4e051a3b00 100644 --- a/website/client/src/pages/private-messages/index.vue +++ b/website/client/src/pages/private-messages/index.vue @@ -679,7 +679,7 @@ import NotificationMixins from '@/mixins/notifications'; // extract to a shared path const CONVERSATIONS_PER_PAGE = 10; -const PM_PER_PAGE = 50; +const PM_PER_PAGE = 10; const UI_STATES = Object.freeze({ LOADING: 'LOADING', diff --git a/website/client/src/store/actions/chat.js b/website/client/src/store/actions/chat.js index 836e6d0f7c..855eba8696 100644 --- a/website/client/src/store/actions/chat.js +++ b/website/client/src/store/actions/chat.js @@ -3,7 +3,7 @@ import Vue from 'vue'; import * as Analytics from '@/libs/analytics'; export async function getChat (store, payload) { - const response = await axios.get(`/api/v4/groups/${payload.groupId}/chat?limit=400`); + const response = await axios.get(`/api/v4/groups/${payload.groupId}/chat`); return response.data.data; } diff --git a/website/server/controllers/api-v3/chat.js b/website/server/controllers/api-v3/chat.js index 32ac046a70..65dce42abe 100644 --- a/website/server/controllers/api-v3/chat.js +++ b/website/server/controllers/api-v3/chat.js @@ -64,8 +64,6 @@ function textContainsBannedSlur (message) { * * @apiParam (Path) {String} groupId The group _id ('party' for the user party and * 'habitrpg' for tavern are accepted). - * @apiParam (Query) {Number} [limit=50] The number of messages to fetch (max 400). - * @apiParam (Query) {String} [before] Fetch messages older than this message ID. * * @apiSuccess {Array} data An array of chat messages * @@ -80,21 +78,18 @@ api.getChat = { const { user } = res.locals; req.checkParams('groupId', apiError('groupIdRequired')).notEmpty(); - req.checkQuery('before').optional().isUUID(); const validationErrors = req.validationErrors(); if (validationErrors) throw validationErrors; const { groupId } = req.params; - const limit = req.query.limit ? Math.min(parseInt(req.query.limit, 10), 400) : 50; - const { before } = req.query; const group = await Group.getGroup({ user, groupId, fields: 'chat privacy' }); if (!group) throw new NotFound(res.t('groupNotFound')); if (group.privacy === 'public') { throw new BadRequest(res.t('featureRetired')); } - const groupChat = await Group.toJSONCleanChat(group, user, { limit, before }); + const groupChat = await Group.toJSONCleanChat(group, user); res.respond(200, groupChat.chat); }, }; diff --git a/website/server/controllers/api-v3/debug.js b/website/server/controllers/api-v3/debug.js index d70eeeeb86..108cf2dbaa 100644 --- a/website/server/controllers/api-v3/debug.js +++ b/website/server/controllers/api-v3/debug.js @@ -2,7 +2,6 @@ import mongoose from 'mongoose'; import get from 'lodash/get'; import sinon from 'sinon'; import moment from 'moment'; -import { v4 as uuid } from 'uuid'; import { authWithHeaders } from '../../middlewares/auth'; import ensureDevelopmentMode from '../../middlewares/ensureDevelopmentMode'; import ensureTimeTravelMode from '../../middlewares/ensureTimeTravelMode'; @@ -12,7 +11,6 @@ import { model as Group, // basicFields as basicGroupFields, } from '../../models/group'; -import { chatModel as Chat, inboxModel as Inbox } from '../../models/message'; import connectToMongoDB from '../../libs/mongoose'; const { content } = common; @@ -313,93 +311,4 @@ api.timeTravelAdjust = { }, }; -api.seedPartyChat = { - method: 'POST', - url: '/debug/seed-party-chat', - middlewares: [ensureDevelopmentMode, authWithHeaders()], - async handler (req, res) { - const { user } = res.locals; - const messageCount = Number(req.body.messageCount); - - if (!Number.isInteger(messageCount) || messageCount < 1) { - throw new BadRequest('messageCount must be a positive integer.'); - } - - if (!user.party._id) { - throw new BadRequest('You are not in a party.'); - } - - const party = await Group.findOne({ _id: user.party._id, type: 'party' }).exec(); - if (!party) { - throw new BadRequest('Party not found.'); - } - - const messages = []; - const baseTimestamp = Date.now(); - - for (let i = 1; i <= messageCount; i += 1) { - const id = uuid(); - messages.push({ - _id: id, - id, - groupId: party._id, - text: `#${i}`, - unformattedText: `#${i}`, - timestamp: new Date(baseTimestamp - (messageCount - i) * 1000), - likes: {}, - flags: {}, - flagCount: 0, - uuid: 'system', - user: 'System', - client: 'debug-seed', - }); - } - - await Chat.insertMany(messages); - - res.respond(200, { messageCount }); - }, -}; - -// Messaging ourselves for testing -api.seedInbox = { - method: 'POST', - url: '/debug/seed-inbox', - middlewares: [ensureDevelopmentMode, authWithHeaders()], - async handler (req, res) { - const { user } = res.locals; - const messageCount = Number(req.body.messageCount); - - if (!Number.isInteger(messageCount) || messageCount < 1) { - throw new BadRequest('messageCount must be a positive integer.'); - } - - const messages = []; - const baseTimestamp = Date.now(); - - for (let i = 1; i <= messageCount; i += 1) { - const id = uuid(); - messages.push({ - _id: id, - id, - ownerId: user._id, - uuid: user._id, - user: user.profile.name, - text: `#${i}`, - unformattedText: `#${i}`, - timestamp: new Date(baseTimestamp - (messageCount - i) * 1000), - likes: {}, - flags: {}, - flagCount: 0, - sent: true, - client: 'debug-seed', - }); - } - - await Inbox.insertMany(messages); - - res.respond(200, { messageCount }); - }, -}; - export default api; diff --git a/website/server/libs/chat/group-chat.js b/website/server/libs/chat/group-chat.js index 028f987b4a..445c72528d 100644 --- a/website/server/libs/chat/group-chat.js +++ b/website/server/libs/chat/group-chat.js @@ -9,9 +9,7 @@ import { // eslint-disable-line import/no-cycle const questScrolls = shared.content.quests; // @TODO: Don't use this method when the group can be saved. -export async function getGroupChat (group, options = {}) { - const { limit, before } = options; - +export async function getGroupChat (group) { let maxChatCount = MAX_CHAT_COUNT; if (group.chatLimitCount && group.chatLimitCount >= MAX_CHAT_COUNT) { maxChatCount = group.chatLimitCount; @@ -19,19 +17,10 @@ export async function getGroupChat (group, options = {}) { maxChatCount = MAX_SUBBED_GROUP_CHAT_COUNT; } - const effectiveLimit = limit !== undefined ? Math.min(limit, maxChatCount) : maxChatCount; - - let query = Chat.find({ groupId: group._id }) - .sort('-timestamp'); - - if (before) { - const beforeMessage = await Chat.findOne({ _id: before }).exec(); - if (beforeMessage) { - query = query.where('timestamp').lt(beforeMessage.timestamp); - } - } - - const groupChat = await query.limit(effectiveLimit).exec(); + const groupChat = await Chat.find({ groupId: group._id }) + .limit(maxChatCount) + .sort('-timestamp') + .exec(); // @TODO: Concat old chat to keep continuity of chat stored on group object const currentGroupChat = group.chat || []; diff --git a/website/server/libs/inbox/index.js b/website/server/libs/inbox/index.js index af0d7ae07d..3cc2c2228b 100644 --- a/website/server/libs/inbox/index.js +++ b/website/server/libs/inbox/index.js @@ -37,9 +37,7 @@ export async function sentMessage (sender, receiver, message, translate) { return messageSent; } -// Paginate per every 50 -const PM_PER_PAGE = 50; -const MAX_PM_COUNT = 400; +const PM_PER_PAGE = 10; const getUserInboxDefaultOptions = { asArray: true, @@ -63,18 +61,12 @@ export async function getUserInbox (user, optionParams = getUserInboxDefaultOpti .sort({ timestamp: -1 }); if (typeof options.page !== 'undefined') { - const page = Number(options.page); - const skip = PM_PER_PAGE * page; - if (skip >= MAX_PM_COUNT) { - return options.asArray ? [] : {}; - } - const remainingAllowed = MAX_PM_COUNT - skip; - const limit = Math.min(PM_PER_PAGE, remainingAllowed); query = query - .skip(skip) - .limit(limit); + .skip(PM_PER_PAGE * Number(options.page)) + .limit(PM_PER_PAGE); } else { - query = query.limit(MAX_PM_COUNT); + // Limit for legacy calls that are not paginated to prevent database issues + query = query.limit(200); } const messages = (await query.lean().exec()).map(msgObj => { diff --git a/website/server/models/group.js b/website/server/models/group.js index 36c678c2cd..7d181c818e 100644 --- a/website/server/models/group.js +++ b/website/server/models/group.js @@ -345,12 +345,12 @@ schema.statics.getGroups = async function getGroups (options = {}) { // unless the user is an admin or said chat is posted by that user // Not putting into toJSON because there we can't access user // It also removes the _meta field that can be stored inside a chat message -schema.statics.toJSONCleanChat = async function groupToJSONCleanChat (group, user, options = {}) { +schema.statics.toJSONCleanChat = async function groupToJSONCleanChat (group, user) { // @TODO: Adding this here for support the old chat, // but we should depreciate accessing chat like this // Also only return chat if requested, eventually we don't want to return chat here if (group && group.chat) { - await getGroupChat(group, options); + await getGroupChat(group); } const groupToJson = group.toJSON();