Cache on edit message (?)

So I've noticed my bot's memory goes up over time, and narrowed it down to this line:
dashboard = await oldDashboard.edit(replyContent);
dashboard = await oldDashboard.edit(replyContent);
I assume editing a message will cache it, but if I have GuildMessageManager: 0 for the make cache, I feel like there's something else happening. I also don't quite think it's a memory leak because 1. if I comment only that line out, the memory is fine and 2. it goes up a bit just after editing the message (the edit is on a set interval to update a few times a minute).
4 Replies
d.js toolkit
d.js toolkit7mo ago
- What's your exact discord.js npm list discord.js and node node -v version? - Not a discord.js issue? Check out #other-js-ts. - Consider reading #how-to-get-help to improve your question! - Explain what exactly your issue is. - Post the full error stack trace, not just the top part! - Show your code! - Issue solved? Press the button! - Marked as resolved by OP
BradyDaLlama .*˖
client = new Client({
intents: [
GatewayIntentBits.Guilds,
GatewayIntentBits.GuildVoiceStates,
],
partials: [Partials.Channel],
makeCache: Options.cacheWithLimits({
...Options.DefaultMakeCacheSettings,
GuildMessageManager: 0,
GuildInviteManager: 0,
GuildEmojiManager: 0,
GuildStickerManager: 0,
GuildMemberManager: {
maxSize: 10,
keepOverLimit: member => member.id === client.user.id
}
}),
});
client = new Client({
intents: [
GatewayIntentBits.Guilds,
GatewayIntentBits.GuildVoiceStates,
],
partials: [Partials.Channel],
makeCache: Options.cacheWithLimits({
...Options.DefaultMakeCacheSettings,
GuildMessageManager: 0,
GuildInviteManager: 0,
GuildEmojiManager: 0,
GuildStickerManager: 0,
GuildMemberManager: {
maxSize: 10,
keepOverLimit: member => member.id === client.user.id
}
}),
});
here's my intents and makeCache stuff also
ShompiFlen
ShompiFlen7mo ago
are you only editing one message every x minutes? also I see the keys you are using for the options for the caches... I dont see those on the documentation <:AA_Menhera_Think:849596324118921216> from where did you get that
BradyDaLlama .*˖
yes, and as for the keys I couldn't find a list of options (the new website is not working great for me) but I saw someone had a similar issue with cache and they fixed it and had these keys. I adjusted the guildMember one but yeah I really dont need stuff cached. its not like it deals with invites or stickers or anything tho, so I can probably remove them
let dashboard;
if(oldDashboard){
dashboard = await oldDashboard.edit(replyContent);
} else {
dashboard = await oldDashboardChannel.send(replyContent);
}
let dashboard;
if(oldDashboard){
dashboard = await oldDashboard.edit(replyContent);
} else {
dashboard = await oldDashboardChannel.send(replyContent);
}
I defined it just above it, but I found that that specific line is what causes the memory to go up by a few mb each time it happens here's the full function:
const Music = require('../../discord/models/Music.js');
const musicDashboard = require('./dashboard.js');

async function updateDashboard(song) {
const dashData = await Music.findOne({guildID: song.member.guild.id, clientID: client.user.id });
let replyContent = await musicDashboard(song.member.voice.channel);

let durationInfo = replyContent.durationInfo;
replyContent = replyContent.content;

let oldDashboardChannel; let oldDashboard;
// --------------- old dashboard declared here --------------------------

if(dashData.dashboard.dashchannel){
oldDashboardChannel = await client.channels.fetch(dashData.dashboard.dashchannel);
}

if(oldDashboardChannel){
oldDashboard = await oldDashboardChannel.messages.fetch(dashData.dashboard?.dashmsg).catch(() => {
oldDashboard = undefined;
})
}

let dashboard;
if(oldDashboard){
dashboard = await oldDashboard.edit(replyContent);
} else {
dashboard = await oldDashboardChannel.send(replyContent);
}

dashData.dashboard.dashchannel = dashboard.channel.id;
dashData.dashboard.dashmsg = dashboard.id;

dashData.markModified('dashboard');
await dashData.save();

let updateDelay = 30

/*if(!dashData.dashboard.updating){
let timer = setInterval(async () => {
let updatedDashData = await Music.findOne({guildID: song.member.guild.id, clientID: client.user.id });
if(!updatedDashData.dashboard.updating){
clearInterval(timer);
return;
}
await updateDashboard(song);
}, updateDelay * 1000);

dashData.dashboard.updating = true;
dashData.markModified('dashboard');
await dashData.save();
}*/
}

module.exports = updateDashboard;
const Music = require('../../discord/models/Music.js');
const musicDashboard = require('./dashboard.js');

async function updateDashboard(song) {
const dashData = await Music.findOne({guildID: song.member.guild.id, clientID: client.user.id });
let replyContent = await musicDashboard(song.member.voice.channel);

let durationInfo = replyContent.durationInfo;
replyContent = replyContent.content;

let oldDashboardChannel; let oldDashboard;
// --------------- old dashboard declared here --------------------------

if(dashData.dashboard.dashchannel){
oldDashboardChannel = await client.channels.fetch(dashData.dashboard.dashchannel);
}

if(oldDashboardChannel){
oldDashboard = await oldDashboardChannel.messages.fetch(dashData.dashboard?.dashmsg).catch(() => {
oldDashboard = undefined;
})
}

let dashboard;
if(oldDashboard){
dashboard = await oldDashboard.edit(replyContent);
} else {
dashboard = await oldDashboardChannel.send(replyContent);
}

dashData.dashboard.dashchannel = dashboard.channel.id;
dashData.dashboard.dashmsg = dashboard.id;

dashData.markModified('dashboard');
await dashData.save();

let updateDelay = 30

/*if(!dashData.dashboard.updating){
let timer = setInterval(async () => {
let updatedDashData = await Music.findOne({guildID: song.member.guild.id, clientID: client.user.id });
if(!updatedDashData.dashboard.updating){
clearInterval(timer);
return;
}
await updateDashboard(song);
}, updateDelay * 1000);

dashData.dashboard.updating = true;
dashData.markModified('dashboard');
await dashData.save();
}*/
}

module.exports = updateDashboard;
the last part is commented out, so that it doesn't try to update the dashboard. Basically if it's not updating, it starts an interval and then saves it to the database that it's updating. I've tested this and it does only start one interval and clear it when you have it stop updating. ik it's kinda an odd way to do this but it's what I was able to do with the database thing (to stop updating when the db updates to tell it to stop) in the ready event it sets it back to not updating, so it starts again. it's just a private bot, but is there a better way to do that? I couldn't really figure out things like cronjob so that i could reference it and cancel it later oldDashboard is declared on line 10ish, ill add a comment
oldDashboard = await oldDashboardChannel.messages.fetch(dashData.dashboard?.dashmsg).catch(() => {
oldDashboard = undefined;
})
oldDashboard = await oldDashboardChannel.messages.fetch(dashData.dashboard?.dashmsg).catch(() => {
oldDashboard = undefined;
})
you mean on this part? (just to make sure I'm on the same page) I think the issue I was running into was it returning an empty collection if the channel was empty, so I just added that iirc but anyways you're saying that fetch will not just limit to the one message? dashData.dashboard.dashmsg in this case is defined and a valid message ID oh yeah that was in the case that it wasn't defined, which obviously I just said it was. I was considering making this a public bot so I wanted to make it robust. but yeah the optional chaining is never regarded because it's always defined. I think I'll remove it there and check if the msg id exists before trying to fetch. no sense trying to check if it exists in the fetch statement (I did just go now and remove that optional chain) it returns an object of content, and a calculated update interval. I don't use the interval anymore because I just hardcoded it at 30 seconds, it's just an option for the future. so reply content is reduced to replyContent.content, which is like { embeds: [responseEmbed], components: [buttonRow], files: [attachment]} it does use canvas to resize it I tried not using the attachment but I think it still made it and just never sent it. let me go test it not creating it at all wow yeah I'm pretty sure that was it. I'll look into why it's caching it each time, and also make it reuse images if it's the same. thanks!