diff --git a/src/commands/misc/reminder.ts b/src/commands/misc/reminder.ts index a5a824b..e01db9f 100644 --- a/src/commands/misc/reminder.ts +++ b/src/commands/misc/reminder.ts @@ -1,9 +1,9 @@ import { ModalActionRowComponentBuilder, SlashCommandBuilder } from '@discordjs/builders'; -import { ActionRowBuilder, ButtonBuilder, ButtonStyle, ChatInputCommandInteraction, Client, Colors, EmbedBuilder, ModalBuilder, TextInputBuilder, TextInputStyle } from 'discord.js'; +import { ActionRowBuilder, ButtonBuilder, ButtonStyle, ChatInputCommandInteraction, Client, ModalBuilder, TextInputBuilder, TextInputStyle } from 'discord.js'; import { collect } from '../../buttons/loader'; import { getLocale, getLocalizations } from '../../utils/locales'; import { getFilename } from '../../utils/misc'; -import { checkOwnershipReminder, deleteReminder, getReminderInfo, newReminder } from '../../utils/reminder'; +import { checkOwnershipReminder, deleteReminder, embedListReminders, getReminderInfo, newReminder } from '../../utils/reminder'; export default { data: (client: Client) => { @@ -186,20 +186,20 @@ export default { // Show modal to user to get at least the time const modal = new ModalBuilder() .setCustomId('reminderGUI') - .setTitle(loc?.get('c_reminder_name').capitalize()); + .setTitle(loc.get('c_reminder_name').capitalize()); const timeGUI = new TextInputBuilder() .setCustomId('reminderGUI-time') - .setLabel(loc?.get('c_reminder_sub1_opt1_name').capitalize()) + .setLabel(loc.get('c_reminder_sub1_opt1_name').capitalize()) .setStyle(TextInputStyle.Short) .setPlaceholder('1h') .setRequired(true); const messageGUI = new TextInputBuilder() .setCustomId('reminderGUI-message') - .setLabel(loc?.get('c_reminder_sub1_opt2_name').capitalize()) + .setLabel(loc.get('c_reminder_sub1_opt2_name').capitalize()) .setStyle(TextInputStyle.Paragraph) - .setPlaceholder(loc?.get('c_reminder_sub1_opt2_desc')) + .setPlaceholder(loc.get('c_reminder_sub1_opt2_desc')) .setRequired(false); modal.addComponents( @@ -239,10 +239,9 @@ export default { collect(client, interaction, idPrec); collect(client, interaction, idNext); - const list = new EmbedBuilder() - .setColor(Colors.DarkGrey) - .setTitle(`List title of ${user.tag}`) - .setDescription('List desc'); + const page = interaction.options.getInteger(loc_default?.get(`c_${filename}_sub2_opt2_name`) as string) ?? 1; + + const list = await embedListReminders(client, user, interaction.guildId, page, interaction.locale); return await interaction.reply({ ephemeral: true, embeds: [list], components: [row] }); } @@ -251,12 +250,12 @@ export default { ?.toLowerCase() ?? '': { const id = interaction.options.getInteger(loc_default?.get(`c_${filename}_sub3_opt1_name`) as string); if (id === null) { - return interaction.reply({ content: loc?.get('c_reminder2'), ephemeral: true }); + return interaction.reply({ content: loc.get('c_reminder2'), ephemeral: true }); } // Check if the ID exists and belongs to the user if (await checkOwnershipReminder(client, id, interaction.user.id, interaction.guildId ?? '0')) { - return interaction.reply({ content: loc?.get('c_reminder3'), ephemeral: true }); + return interaction.reply({ content: loc.get('c_reminder3'), ephemeral: true }); } // Stop timeout @@ -264,7 +263,7 @@ export default { clearTimeout(reminderInfo.timeout_id); // Delete from database - deleteReminder(client, reminderInfo.creation_date, reminderInfo.user_id); + deleteReminder(client, Number(reminderInfo.creation_date), reminderInfo.user_id); return interaction.reply({ content: `Reminder **#${id}** supprimé !`, ephemeral: true }); } diff --git a/src/locales/fr.json b/src/locales/fr.json index 4c38ffd..632114d 100644 --- a/src/locales/fr.json +++ b/src/locales/fr.json @@ -39,5 +39,10 @@ "c_reminder1": "Un rappel a été configuré pour dans", "c_reminder2": "L'ID renseigné n'est pas valide.", "c_reminder3": "Rappel non trouvé, pas sur le bon serveur ou qui ne vous appartiens pas.", - "c_reminder4": "Utilisateur inconnu." + "c_reminder4": "Utilisateur inconnu.", + "c_reminder5": "Rappels de", + "c_reminder6": "Page ", + "c_reminder7": "Pas de message", + "c_reminder8": "Expire dans", + "c_reminder9": "Fais le" } diff --git a/src/utils/reminder.ts b/src/utils/reminder.ts index ad23b2c..0e455b8 100644 --- a/src/utils/reminder.ts +++ b/src/utils/reminder.ts @@ -1,6 +1,6 @@ -import { Client } from 'discord.js'; +import { Client, Colors, EmbedBuilder, User } from 'discord.js'; import { getLocale } from './locales'; -import { strToSeconds } from './time'; +import { showDate, strToSeconds, timeDeltaToString } from './time'; /** * Option possible for reminders @@ -32,11 +32,11 @@ export type dbReminder = { expiration_date: number, option_id: OptionReminder, channel_id: string | null, - creation_date: number, + creation_date: string, user_id: string, guild_id: string | null, locale: string, - timeout_id: number + timeout_id: string } /** @@ -243,3 +243,67 @@ export const updateReminder = (client: Client, data: dbReminder) => { }); }); }; + +/** + * Return a list of reminders for a user in a specified context + * @param client Client + * @param userId user ID + * @param guildId guild ID + * @returns List of reminders of a user in a guild + */ +const listReminders = async (client: Client, userId: string, guildId: string | null) => { + return await new Promise((ok, ko) => { + // Check the ownership + client.db.all('SELECT data, creation_date, expiration_date, id FROM reminder \ + WHERE user_id = ? AND (guild_id = ? OR guild_id = 0)', [ + userId, guildId ?? 0], (err, row) => { + if (err) { + ko(err); + } + + // Send all the current reminders + ok(row); + }); + }) as dbReminder[]; +}; + +export const embedListReminders = async (client: Client, user: User, guildId: string | null, page: number, local: string) => { + const loc = getLocale(client, local); + const reminders = await listReminders(client, user.id, guildId); + + const elementPerPage = 5; + let pageMax = Math.floor(reminders.length / elementPerPage); + + if (pageMax <= 1) { + page = 1; + pageMax = 1; + } + const embed = new EmbedBuilder() + .setColor(Colors.DarkGrey) + .setDescription(`${loc.get('c_reminder5')} ${user} • ${loc.get('c_reminder6')} ${page}/${pageMax}`) + .setThumbnail(user.displayAvatarURL()); + + const limit = elementPerPage * page; + + if (reminders.length > 0 && page <= pageMax) { + let curseur = limit - elementPerPage - 1; + reminders.forEach((remind) => { + if (curseur <= limit) { + let text = remind.data ?? loc.get('c_reminder7'); + if (text.length > 1024) { + text = `${text.substring(0, 1021)}...`; + } + const expiration = `${loc.get('c_reminder8')} ${timeDeltaToString(remind.expiration_date)}`; + embed.addFields({ + name: `#${remind.id} • ${loc.get('c_reminder9')} ${showDate(local, loc, new Date(Number(remind.creation_date)))}\n${expiration}`, + value: text, + inline: false, + }); + + curseur++; + } + }); + } + + return embed; +}; diff --git a/src/utils/time.ts b/src/utils/time.ts index bbbc6f5..4618b8b 100644 --- a/src/utils/time.ts +++ b/src/utils/time.ts @@ -41,3 +41,14 @@ export const strToSeconds = (time: string) => { return res; }; + +/** + * Calculating the difference between a date and now + * @param time Time + * @returns Delta between the time and now + */ +export const timeDeltaToString = (time: number) => { + const now = Date.now(); + // TODO adapt the output and not always parse the time as seconds + return `${strToSeconds(`${now - time}`)} secs`; +};