mirror of
https://github.com/TheShadowEevee/Konpeki-Discord-Bot.git
synced 2025-01-11 14:38:49 -06:00
Updated formatting
This commit is contained in:
parent
ecbd2bdc4e
commit
25346f9ab2
11 changed files with 601 additions and 601 deletions
|
@ -9,24 +9,24 @@ const { SlashCommandBuilder, EmbedBuilder } = require('discord.js');
|
||||||
const { clientId, botName, botOwner } = require('../config.json');
|
const { clientId, botName, botOwner } = require('../config.json');
|
||||||
|
|
||||||
module.exports = {
|
module.exports = {
|
||||||
data: new SlashCommandBuilder()
|
data: new SlashCommandBuilder()
|
||||||
.setName('about')
|
.setName('about')
|
||||||
.setDescription('Gives basic information about the bot'),
|
.setDescription('Gives basic information about the bot'),
|
||||||
async execute(interaction) {
|
async execute(interaction) {
|
||||||
|
|
||||||
const exampleEmbed = new EmbedBuilder()
|
const exampleEmbed = new EmbedBuilder()
|
||||||
.setColor(interaction.member.displayHexColor)
|
.setColor(interaction.member.displayHexColor)
|
||||||
.setTitle(`About ${botName}`)
|
.setTitle(`About ${botName}`)
|
||||||
.setURL(`https://discord.com/oauth2/authorize?client_id=${clientId}&permissions=274877908992&scope=bot%20applications.commands`)
|
.setURL(`https://discord.com/oauth2/authorize?client_id=${clientId}&permissions=274877908992&scope=bot%20applications.commands`)
|
||||||
.addFields(
|
.addFields(
|
||||||
{ name: 'Admin of this bot', value: `${botOwner}` },
|
{ name: 'Admin of this bot', value: `${botOwner}` },
|
||||||
{ name: 'Websocket Heartbeat / Ping', value: `${interaction.client.ws.ping}ms` },
|
{ name: 'Websocket Heartbeat / Ping', value: `${interaction.client.ws.ping}ms` },
|
||||||
{ name: 'Invite Link', value: `https://discord.com/oauth2/authorize?client_id=${clientId}&permissions=274877908992&scope=bot%20applications.commands`, inline: true },
|
{ name: 'Invite Link', value: `https://discord.com/oauth2/authorize?client_id=${clientId}&permissions=274877908992&scope=bot%20applications.commands`, inline: true },
|
||||||
{ name: 'Based on the open source Konpeki Discord Bot', value: 'https://github.com/TheShadowEevee/Konpeki-Discord-Bot', inline: true },
|
{ name: 'Based on the open source Konpeki Discord Bot', value: 'https://github.com/TheShadowEevee/Konpeki-Discord-Bot', inline: true },
|
||||||
)
|
)
|
||||||
.setFooter({ text: `Support for custom changes should go through the admin of this bot, ${botOwner}. Support for the underlying Konpeki Discord Bot is available at https://discord.gg/Zt8zruXexJ.` });
|
.setFooter({ text: `Support for custom changes should go through the admin of this bot, ${botOwner}. Support for the underlying Konpeki Discord Bot is available at https://discord.gg/Zt8zruXexJ.` });
|
||||||
|
|
||||||
|
|
||||||
await interaction.reply({ embeds: [exampleEmbed], ephemeral: true });
|
await interaction.reply({ embeds: [exampleEmbed], ephemeral: true });
|
||||||
},
|
},
|
||||||
};
|
};
|
|
@ -6,62 +6,62 @@
|
||||||
const { SlashCommandBuilder } = require('discord.js');
|
const { SlashCommandBuilder } = require('discord.js');
|
||||||
|
|
||||||
module.exports = {
|
module.exports = {
|
||||||
data: new SlashCommandBuilder()
|
data: new SlashCommandBuilder()
|
||||||
.setName('avatar')
|
.setName('avatar')
|
||||||
.setDescription('Shares a users current avatar')
|
.setDescription('Shares a users current avatar')
|
||||||
|
|
||||||
// Optional user selection for avatar target; target selves if none.
|
// Optional user selection for avatar target; target selves if none.
|
||||||
.addUserOption(option =>
|
.addUserOption(option =>
|
||||||
option.setName('user')
|
option.setName('user')
|
||||||
.setDescription('Select the user to get an avatar from'))
|
.setDescription('Select the user to get an avatar from'))
|
||||||
|
|
||||||
// Optional choice for user to choose avatar size; 4096 if no selection.
|
// Optional choice for user to choose avatar size; 4096 if no selection.
|
||||||
.addStringOption(option =>
|
.addStringOption(option =>
|
||||||
option.setName('format')
|
option.setName('format')
|
||||||
.setDescription('Select what format you want the output to be')
|
.setDescription('Select what format you want the output to be')
|
||||||
.addChoices(
|
.addChoices(
|
||||||
{ name: 'WebP', value: 'webp' },
|
{ name: 'WebP', value: 'webp' },
|
||||||
{ name: 'PNG', value: 'png' },
|
{ name: 'PNG', value: 'png' },
|
||||||
{ name: 'JPEG', value: 'jpg' },
|
{ name: 'JPEG', value: 'jpg' },
|
||||||
))
|
))
|
||||||
|
|
||||||
|
|
||||||
// Optional choice for user to choose avatar format; webp if no selection.
|
// Optional choice for user to choose avatar format; webp if no selection.
|
||||||
.addStringOption(option =>
|
.addStringOption(option =>
|
||||||
option.setName('size')
|
option.setName('size')
|
||||||
.setDescription('Select what size you want the output to be')
|
.setDescription('Select what size you want the output to be')
|
||||||
.addChoices(
|
.addChoices(
|
||||||
{ name: '4096px', value: '4096' },
|
{ name: '4096px', value: '4096' },
|
||||||
{ name: '2048px', value: '2048' },
|
{ name: '2048px', value: '2048' },
|
||||||
{ name: '1024px', value: '1024' },
|
{ name: '1024px', value: '1024' },
|
||||||
{ name: '600px', value: '600' },
|
{ name: '600px', value: '600' },
|
||||||
{ name: '512px', value: '512' },
|
{ name: '512px', value: '512' },
|
||||||
{ name: '300px', value: '300' },
|
{ name: '300px', value: '300' },
|
||||||
{ name: '256px', value: '256' },
|
{ name: '256px', value: '256' },
|
||||||
{ name: '128px', value: '128' },
|
{ name: '128px', value: '128' },
|
||||||
{ name: '96px', value: '96' },
|
{ name: '96px', value: '96' },
|
||||||
{ name: '64px', value: '64' },
|
{ name: '64px', value: '64' },
|
||||||
{ name: '56px', value: '56' },
|
{ name: '56px', value: '56' },
|
||||||
{ name: '32px', value: '32' },
|
{ name: '32px', value: '32' },
|
||||||
{ name: '16px', value: '16' },
|
{ name: '16px', value: '16' },
|
||||||
))
|
))
|
||||||
|
|
||||||
|
|
||||||
// Optional Ephemeral check to allow user to choose command results to be shared publicly or private; send to self only if no selection.
|
// Optional Ephemeral check to allow user to choose command results to be shared publicly or private; send to self only if no selection.
|
||||||
.addStringOption(option =>
|
.addStringOption(option =>
|
||||||
option.setName('ephemeral')
|
option.setName('ephemeral')
|
||||||
.setDescription('Post the avatar in the current channel')
|
.setDescription('Post the avatar in the current channel')
|
||||||
.addChoices(
|
.addChoices(
|
||||||
{ name: 'Send to me only', value: 'true' },
|
{ name: 'Send to me only', value: 'true' },
|
||||||
{ name: 'Send in channel', value: 'false' },
|
{ name: 'Send in channel', value: 'false' },
|
||||||
)),
|
)),
|
||||||
|
|
||||||
async execute(interaction) {
|
async execute(interaction) {
|
||||||
const discordUser = interaction.options.getUser('user') ?? interaction.user;
|
const discordUser = interaction.options.getUser('user') ?? interaction.user;
|
||||||
const avatarFormat = interaction.options.getString('format') ?? 'webp';
|
const avatarFormat = interaction.options.getString('format') ?? 'webp';
|
||||||
const avatarSize = Number(interaction.options.getString('size')) ?? 4096;
|
const avatarSize = Number(interaction.options.getString('size')) ?? 4096;
|
||||||
const isEphemeral = interaction.options.getString('ephemeral') ?? 'true';
|
const isEphemeral = interaction.options.getString('ephemeral') ?? 'true';
|
||||||
|
|
||||||
await interaction.reply({ content: `${discordUser.avatarURL({ extension:avatarFormat, size:avatarSize, forceStatic:false })}`, ephemeral: (isEphemeral === 'true') });
|
await interaction.reply({ content: `${discordUser.avatarURL({ extension:avatarFormat, size:avatarSize, forceStatic:false })}`, ephemeral: (isEphemeral === 'true') });
|
||||||
},
|
},
|
||||||
};
|
};
|
436
commands/help.js
436
commands/help.js
|
@ -11,258 +11,258 @@ let helpFile = '';
|
||||||
|
|
||||||
// Import help text file
|
// Import help text file
|
||||||
if (fs.existsSync('./data/help-text.json')) {
|
if (fs.existsSync('./data/help-text.json')) {
|
||||||
helpFile = JSON.parse(fs.readFileSync('./data/help-text.json', 'utf8'));
|
helpFile = JSON.parse(fs.readFileSync('./data/help-text.json', 'utf8'));
|
||||||
}
|
}
|
||||||
|
|
||||||
// List of all commands, by category
|
// List of all commands, by category
|
||||||
// Command help, listing options.
|
// Command help, listing options.
|
||||||
module.exports = {
|
module.exports = {
|
||||||
data: new SlashCommandBuilder()
|
data: new SlashCommandBuilder()
|
||||||
.setName('help')
|
.setName('help')
|
||||||
.setDescription('Provides information on avalible commands')
|
.setDescription('Provides information on avalible commands')
|
||||||
|
|
||||||
// Allow choosing the help page to open
|
// Allow choosing the help page to open
|
||||||
.addNumberOption(option =>
|
.addNumberOption(option =>
|
||||||
option.setName('page')
|
option.setName('page')
|
||||||
.setDescription('Choose help page to skip to'),
|
.setDescription('Choose help page to skip to'),
|
||||||
),
|
),
|
||||||
|
|
||||||
async execute(interaction) {
|
async execute(interaction) {
|
||||||
|
|
||||||
let pageNumber = interaction.options.getNumber('page') ?? 1;
|
let pageNumber = interaction.options.getNumber('page') ?? 1;
|
||||||
const commandsPerPage = 5;
|
const commandsPerPage = 5;
|
||||||
let commandsThisPage = 0;
|
let commandsThisPage = 0;
|
||||||
|
|
||||||
const numberOfCommands = Object.keys(helpFile).length;
|
const numberOfCommands = Object.keys(helpFile).length;
|
||||||
const pageTotal = String(Math.ceil(numberOfCommands / commandsPerPage));
|
const pageTotal = String(Math.ceil(numberOfCommands / commandsPerPage));
|
||||||
let userRoleColor = Number('0x' + interaction.member.displayHexColor.split('#')[1]);
|
let userRoleColor = Number('0x' + interaction.member.displayHexColor.split('#')[1]);
|
||||||
|
|
||||||
// This will also unintentionally catch roles with full black color (#000000), but it should be fine.
|
// This will also unintentionally catch roles with full black color (#000000), but it should be fine.
|
||||||
if (userRoleColor == 0) {
|
if (userRoleColor == 0) {
|
||||||
userRoleColor = Number(0x55ffff);
|
userRoleColor = Number(0x55ffff);
|
||||||
}
|
}
|
||||||
|
|
||||||
if (pageNumber > pageTotal) {
|
if (pageNumber > pageTotal) {
|
||||||
pageNumber = 1;
|
pageNumber = 1;
|
||||||
}
|
}
|
||||||
|
|
||||||
let embedPartOne = {
|
let embedPartOne = {
|
||||||
color: userRoleColor,
|
color: userRoleColor,
|
||||||
title: 'Help Text',
|
title: 'Help Text',
|
||||||
description: `Page ${pageNumber} of ${pageTotal}`,
|
description: `Page ${pageNumber} of ${pageTotal}`,
|
||||||
};
|
};
|
||||||
|
|
||||||
if (pageNumber != pageTotal) {
|
if (pageNumber != pageTotal) {
|
||||||
commandsThisPage = commandsPerPage;
|
commandsThisPage = commandsPerPage;
|
||||||
}
|
}
|
||||||
else {
|
else {
|
||||||
commandsThisPage = numberOfCommands % commandsPerPage;
|
commandsThisPage = numberOfCommands % commandsPerPage;
|
||||||
}
|
}
|
||||||
|
|
||||||
let embedPartTwo = '';
|
let embedPartTwo = '';
|
||||||
|
|
||||||
embedPartTwo += '{"fields": [';
|
embedPartTwo += '{"fields": [';
|
||||||
for (let i = 0; i < commandsThisPage; i++) {
|
for (let i = 0; i < commandsThisPage; i++) {
|
||||||
|
|
||||||
const currentCommandName = Object.keys(helpFile)[i + (commandsPerPage * (pageNumber - 1))];
|
const currentCommandName = Object.keys(helpFile)[i + (commandsPerPage * (pageNumber - 1))];
|
||||||
|
|
||||||
embedPartTwo += '{';
|
embedPartTwo += '{';
|
||||||
|
|
||||||
embedPartTwo += ' "name": "/' + currentCommandName + '",',
|
embedPartTwo += ' "name": "/' + currentCommandName + '",',
|
||||||
embedPartTwo += ' "value": "' + helpFile[currentCommandName].description + '"',
|
embedPartTwo += ' "value": "' + helpFile[currentCommandName].description + '"',
|
||||||
|
|
||||||
embedPartTwo += '},';
|
embedPartTwo += '},';
|
||||||
}
|
}
|
||||||
embedPartTwo = embedPartTwo.substring(0, embedPartTwo.length - 1) + ']}';
|
embedPartTwo = embedPartTwo.substring(0, embedPartTwo.length - 1) + ']}';
|
||||||
|
|
||||||
let buttonList = '';
|
let buttonList = '';
|
||||||
|
|
||||||
// Change buttons based on page number. Is there an easier/shorter way to do this?
|
// Change buttons based on page number. Is there an easier/shorter way to do this?
|
||||||
if (pageNumber == 1) {
|
if (pageNumber == 1) {
|
||||||
buttonList = new ActionRowBuilder()
|
buttonList = new ActionRowBuilder()
|
||||||
.addComponents(
|
.addComponents(
|
||||||
new ButtonBuilder()
|
new ButtonBuilder()
|
||||||
.setCustomId('back')
|
.setCustomId('back')
|
||||||
.setLabel('Previous')
|
.setLabel('Previous')
|
||||||
.setStyle(ButtonStyle.Secondary)
|
.setStyle(ButtonStyle.Secondary)
|
||||||
.setDisabled(true),
|
.setDisabled(true),
|
||||||
)
|
)
|
||||||
.addComponents(
|
.addComponents(
|
||||||
new ButtonBuilder()
|
new ButtonBuilder()
|
||||||
.setCustomId('page')
|
.setCustomId('page')
|
||||||
.setLabel(`${pageNumber}/${pageTotal}`)
|
.setLabel(`${pageNumber}/${pageTotal}`)
|
||||||
.setStyle(ButtonStyle.Secondary)
|
.setStyle(ButtonStyle.Secondary)
|
||||||
.setDisabled(true),
|
.setDisabled(true),
|
||||||
)
|
)
|
||||||
.addComponents(
|
.addComponents(
|
||||||
new ButtonBuilder()
|
new ButtonBuilder()
|
||||||
.setCustomId('next')
|
.setCustomId('next')
|
||||||
.setLabel('Next')
|
.setLabel('Next')
|
||||||
.setStyle(ButtonStyle.Primary),
|
.setStyle(ButtonStyle.Primary),
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
else if (pageNumber == pageTotal) {
|
else if (pageNumber == pageTotal) {
|
||||||
buttonList = new ActionRowBuilder()
|
buttonList = new ActionRowBuilder()
|
||||||
.addComponents(
|
.addComponents(
|
||||||
new ButtonBuilder()
|
new ButtonBuilder()
|
||||||
.setCustomId('back')
|
.setCustomId('back')
|
||||||
.setLabel('Previous')
|
.setLabel('Previous')
|
||||||
.setStyle(ButtonStyle.Primary),
|
.setStyle(ButtonStyle.Primary),
|
||||||
)
|
)
|
||||||
.addComponents(
|
.addComponents(
|
||||||
new ButtonBuilder()
|
new ButtonBuilder()
|
||||||
.setCustomId('page')
|
.setCustomId('page')
|
||||||
.setLabel(`${pageNumber}/${pageTotal}`)
|
.setLabel(`${pageNumber}/${pageTotal}`)
|
||||||
.setStyle(ButtonStyle.Secondary)
|
.setStyle(ButtonStyle.Secondary)
|
||||||
.setDisabled(true),
|
.setDisabled(true),
|
||||||
)
|
)
|
||||||
.addComponents(
|
.addComponents(
|
||||||
new ButtonBuilder()
|
new ButtonBuilder()
|
||||||
.setCustomId('next')
|
.setCustomId('next')
|
||||||
.setLabel('Next')
|
.setLabel('Next')
|
||||||
.setStyle(ButtonStyle.Secondary)
|
.setStyle(ButtonStyle.Secondary)
|
||||||
.setDisabled(true),
|
.setDisabled(true),
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
else {
|
else {
|
||||||
buttonList = new ActionRowBuilder()
|
buttonList = new ActionRowBuilder()
|
||||||
.addComponents(
|
.addComponents(
|
||||||
new ButtonBuilder()
|
new ButtonBuilder()
|
||||||
.setCustomId('back')
|
.setCustomId('back')
|
||||||
.setLabel('Previous')
|
.setLabel('Previous')
|
||||||
.setStyle(ButtonStyle.Primary),
|
.setStyle(ButtonStyle.Primary),
|
||||||
)
|
)
|
||||||
.addComponents(
|
.addComponents(
|
||||||
new ButtonBuilder()
|
new ButtonBuilder()
|
||||||
.setCustomId('page')
|
.setCustomId('page')
|
||||||
.setLabel(`${pageNumber}/${pageTotal}`)
|
.setLabel(`${pageNumber}/${pageTotal}`)
|
||||||
.setStyle(ButtonStyle.Secondary)
|
.setStyle(ButtonStyle.Secondary)
|
||||||
.setDisabled(true),
|
.setDisabled(true),
|
||||||
)
|
)
|
||||||
.addComponents(
|
.addComponents(
|
||||||
new ButtonBuilder()
|
new ButtonBuilder()
|
||||||
.setCustomId('next')
|
.setCustomId('next')
|
||||||
.setLabel('Next')
|
.setLabel('Next')
|
||||||
.setStyle(ButtonStyle.Primary),
|
.setStyle(ButtonStyle.Primary),
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
// Button code
|
// Button code
|
||||||
const collector = interaction.channel.createMessageComponentCollector({ time: 300000 });
|
const collector = interaction.channel.createMessageComponentCollector({ time: 300000 });
|
||||||
|
|
||||||
collector.on('collect', async i => {
|
collector.on('collect', async i => {
|
||||||
|
|
||||||
if (i.customId === 'next') {
|
if (i.customId === 'next') {
|
||||||
pageNumber += 1;
|
pageNumber += 1;
|
||||||
}
|
}
|
||||||
if (i.customId === 'back') {
|
if (i.customId === 'back') {
|
||||||
pageNumber -= 1;
|
pageNumber -= 1;
|
||||||
}
|
}
|
||||||
|
|
||||||
// Replicate the above code to remake the help model for the new page. Again, there has to be an easier way to do this.
|
// Replicate the above code to remake the help model for the new page. Again, there has to be an easier way to do this.
|
||||||
embedPartOne = {
|
embedPartOne = {
|
||||||
color: userRoleColor,
|
color: userRoleColor,
|
||||||
title: 'Help Text',
|
title: 'Help Text',
|
||||||
description: `Page ${pageNumber} of ${pageTotal}`,
|
description: `Page ${pageNumber} of ${pageTotal}`,
|
||||||
};
|
};
|
||||||
|
|
||||||
embedPartTwo = '';
|
embedPartTwo = '';
|
||||||
|
|
||||||
if (pageNumber != pageTotal) {
|
if (pageNumber != pageTotal) {
|
||||||
commandsThisPage = commandsPerPage;
|
commandsThisPage = commandsPerPage;
|
||||||
}
|
}
|
||||||
else {
|
else {
|
||||||
commandsThisPage = numberOfCommands % commandsPerPage;
|
commandsThisPage = numberOfCommands % commandsPerPage;
|
||||||
}
|
}
|
||||||
|
|
||||||
embedPartTwo += '{"fields": [';
|
embedPartTwo += '{"fields": [';
|
||||||
for (let j = 0; j < commandsThisPage; j++) {
|
for (let j = 0; j < commandsThisPage; j++) {
|
||||||
|
|
||||||
const currentCommandName = Object.keys(helpFile)[j + (commandsPerPage * (pageNumber - 1))];
|
const currentCommandName = Object.keys(helpFile)[j + (commandsPerPage * (pageNumber - 1))];
|
||||||
|
|
||||||
embedPartTwo += '{';
|
embedPartTwo += '{';
|
||||||
|
|
||||||
embedPartTwo += ' "name": "/' + currentCommandName + '",',
|
embedPartTwo += ' "name": "/' + currentCommandName + '",',
|
||||||
embedPartTwo += ' "value": "' + helpFile[currentCommandName].description + '"',
|
embedPartTwo += ' "value": "' + helpFile[currentCommandName].description + '"',
|
||||||
|
|
||||||
embedPartTwo += '},';
|
embedPartTwo += '},';
|
||||||
}
|
}
|
||||||
embedPartTwo = embedPartTwo.substring(0, embedPartTwo.length - 1) + ']}';
|
embedPartTwo = embedPartTwo.substring(0, embedPartTwo.length - 1) + ']}';
|
||||||
|
|
||||||
// Change buttons based on page number. Is there an easier/shorter way to do this?
|
// Change buttons based on page number. Is there an easier/shorter way to do this?
|
||||||
if (pageNumber == 1) {
|
if (pageNumber == 1) {
|
||||||
buttonList = new ActionRowBuilder()
|
buttonList = new ActionRowBuilder()
|
||||||
.addComponents(
|
.addComponents(
|
||||||
new ButtonBuilder()
|
new ButtonBuilder()
|
||||||
.setCustomId('back')
|
.setCustomId('back')
|
||||||
.setLabel('Previous')
|
.setLabel('Previous')
|
||||||
.setStyle(ButtonStyle.Secondary)
|
.setStyle(ButtonStyle.Secondary)
|
||||||
.setDisabled(true),
|
.setDisabled(true),
|
||||||
)
|
)
|
||||||
.addComponents(
|
.addComponents(
|
||||||
new ButtonBuilder()
|
new ButtonBuilder()
|
||||||
.setCustomId('page')
|
.setCustomId('page')
|
||||||
.setLabel(`${pageNumber}/${pageTotal}`)
|
.setLabel(`${pageNumber}/${pageTotal}`)
|
||||||
.setStyle(ButtonStyle.Secondary)
|
.setStyle(ButtonStyle.Secondary)
|
||||||
.setDisabled(true),
|
.setDisabled(true),
|
||||||
)
|
)
|
||||||
.addComponents(
|
.addComponents(
|
||||||
new ButtonBuilder()
|
new ButtonBuilder()
|
||||||
.setCustomId('next')
|
.setCustomId('next')
|
||||||
.setLabel('Next')
|
.setLabel('Next')
|
||||||
.setStyle(ButtonStyle.Primary),
|
.setStyle(ButtonStyle.Primary),
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
else if (pageNumber == pageTotal) {
|
else if (pageNumber == pageTotal) {
|
||||||
buttonList = new ActionRowBuilder()
|
buttonList = new ActionRowBuilder()
|
||||||
.addComponents(
|
.addComponents(
|
||||||
new ButtonBuilder()
|
new ButtonBuilder()
|
||||||
.setCustomId('back')
|
.setCustomId('back')
|
||||||
.setLabel('Previous')
|
.setLabel('Previous')
|
||||||
.setStyle(ButtonStyle.Primary),
|
.setStyle(ButtonStyle.Primary),
|
||||||
)
|
)
|
||||||
.addComponents(
|
.addComponents(
|
||||||
new ButtonBuilder()
|
new ButtonBuilder()
|
||||||
.setCustomId('page')
|
.setCustomId('page')
|
||||||
.setLabel(`${pageNumber}/${pageTotal}`)
|
.setLabel(`${pageNumber}/${pageTotal}`)
|
||||||
.setStyle(ButtonStyle.Secondary)
|
.setStyle(ButtonStyle.Secondary)
|
||||||
.setDisabled(true),
|
.setDisabled(true),
|
||||||
)
|
)
|
||||||
.addComponents(
|
.addComponents(
|
||||||
new ButtonBuilder()
|
new ButtonBuilder()
|
||||||
.setCustomId('next')
|
.setCustomId('next')
|
||||||
.setLabel('Next')
|
.setLabel('Next')
|
||||||
.setStyle(ButtonStyle.Secondary)
|
.setStyle(ButtonStyle.Secondary)
|
||||||
.setDisabled(true),
|
.setDisabled(true),
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
else {
|
else {
|
||||||
buttonList = new ActionRowBuilder()
|
buttonList = new ActionRowBuilder()
|
||||||
.addComponents(
|
.addComponents(
|
||||||
new ButtonBuilder()
|
new ButtonBuilder()
|
||||||
.setCustomId('back')
|
.setCustomId('back')
|
||||||
.setLabel('Previous')
|
.setLabel('Previous')
|
||||||
.setStyle(ButtonStyle.Primary),
|
.setStyle(ButtonStyle.Primary),
|
||||||
)
|
)
|
||||||
.addComponents(
|
.addComponents(
|
||||||
new ButtonBuilder()
|
new ButtonBuilder()
|
||||||
.setCustomId('page')
|
.setCustomId('page')
|
||||||
.setLabel(`${pageNumber}/${pageTotal}`)
|
.setLabel(`${pageNumber}/${pageTotal}`)
|
||||||
.setStyle(ButtonStyle.Secondary)
|
.setStyle(ButtonStyle.Secondary)
|
||||||
.setDisabled(true),
|
.setDisabled(true),
|
||||||
)
|
)
|
||||||
.addComponents(
|
.addComponents(
|
||||||
new ButtonBuilder()
|
new ButtonBuilder()
|
||||||
.setCustomId('next')
|
.setCustomId('next')
|
||||||
.setLabel('Next')
|
.setLabel('Next')
|
||||||
.setStyle(ButtonStyle.Primary),
|
.setStyle(ButtonStyle.Primary),
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
await i.update({ embeds: [Object.assign({}, embedPartOne, JSON.parse(embedPartTwo))], components: [ buttonList ], ephemeral: true });
|
await i.update({ embeds: [Object.assign({}, embedPartOne, JSON.parse(embedPartTwo))], components: [ buttonList ], ephemeral: true });
|
||||||
});
|
});
|
||||||
|
|
||||||
await interaction.reply({ embeds: [Object.assign({}, embedPartOne, JSON.parse(embedPartTwo))], components: [ buttonList ], ephemeral: true });
|
await interaction.reply({ embeds: [Object.assign({}, embedPartOne, JSON.parse(embedPartTwo))], components: [ buttonList ], ephemeral: true });
|
||||||
|
|
||||||
},
|
},
|
||||||
};
|
};
|
|
@ -9,10 +9,10 @@ const { SlashCommandBuilder } = require('discord.js');
|
||||||
const { botName, clientId } = require('../config.json');
|
const { botName, clientId } = require('../config.json');
|
||||||
|
|
||||||
module.exports = {
|
module.exports = {
|
||||||
data: new SlashCommandBuilder()
|
data: new SlashCommandBuilder()
|
||||||
.setName('invite')
|
.setName('invite')
|
||||||
.setDescription(`Invite ${botName} to your own server`),
|
.setDescription(`Invite ${botName} to your own server`),
|
||||||
async execute(interaction) {
|
async execute(interaction) {
|
||||||
await interaction.reply({ content: `Use this link to invite ${botName} (That's me!) to your own server!\nhttps://discord.com/oauth2/authorize?client_id=${clientId}&permissions=274877908992&scope=bot%20applications.commands`, ephemeral: true });
|
await interaction.reply({ content: `Use this link to invite ${botName} (That's me!) to your own server!\nhttps://discord.com/oauth2/authorize?client_id=${clientId}&permissions=274877908992&scope=bot%20applications.commands`, ephemeral: true });
|
||||||
},
|
},
|
||||||
};
|
};
|
|
@ -7,69 +7,69 @@ const { SlashCommandBuilder } = require('discord.js');
|
||||||
const { randomInt } = require('node:crypto');
|
const { randomInt } = require('node:crypto');
|
||||||
|
|
||||||
module.exports = {
|
module.exports = {
|
||||||
data: new SlashCommandBuilder()
|
data: new SlashCommandBuilder()
|
||||||
.setName('lottery')
|
.setName('lottery')
|
||||||
.setDescription('Rolls a set of numbers you can use for whatever')
|
.setDescription('Rolls a set of numbers you can use for whatever')
|
||||||
|
|
||||||
// Get number of numbers to roll
|
// Get number of numbers to roll
|
||||||
.addNumberOption(option =>
|
.addNumberOption(option =>
|
||||||
option.setName('count')
|
option.setName('count')
|
||||||
.setDescription('How many numbers to roll'),
|
.setDescription('How many numbers to roll'),
|
||||||
)
|
)
|
||||||
|
|
||||||
// Get max number to roll
|
// Get max number to roll
|
||||||
.addNumberOption(option =>
|
.addNumberOption(option =>
|
||||||
option.setName('max')
|
option.setName('max')
|
||||||
.setDescription('Set the maximum roll'),
|
.setDescription('Set the maximum roll'),
|
||||||
)
|
)
|
||||||
|
|
||||||
// Optional Ephemeral check to allow user to choose command results to be shared publicly or private; send to self only if no selection.
|
// Optional Ephemeral check to allow user to choose command results to be shared publicly or private; send to self only if no selection.
|
||||||
.addStringOption(option =>
|
.addStringOption(option =>
|
||||||
option.setName('ephemeral')
|
option.setName('ephemeral')
|
||||||
.setDescription('Post the avatar in the current channel')
|
.setDescription('Post the avatar in the current channel')
|
||||||
.addChoices(
|
.addChoices(
|
||||||
{ name: 'Send to me only', value: 'true' },
|
{ name: 'Send to me only', value: 'true' },
|
||||||
{ name: 'Send in channel', value: 'false' },
|
{ name: 'Send in channel', value: 'false' },
|
||||||
)),
|
)),
|
||||||
|
|
||||||
async execute(interaction) {
|
async execute(interaction) {
|
||||||
const isEphemeral = interaction.options.getString('ephemeral') ?? 'true';
|
const isEphemeral = interaction.options.getString('ephemeral') ?? 'true';
|
||||||
const rollCount = interaction.options.getNumber('count') ?? 6;
|
const rollCount = interaction.options.getNumber('count') ?? 6;
|
||||||
const maxRoll = interaction.options.getNumber('max') ?? 99;
|
const maxRoll = interaction.options.getNumber('max') ?? 99;
|
||||||
|
|
||||||
// Limit max number rollable to prevent spam and API issues
|
// Limit max number rollable to prevent spam and API issues
|
||||||
if (maxRoll > 999) {
|
if (maxRoll > 999) {
|
||||||
await interaction.reply({ content: `Big roller! Unfortunatly ${maxRoll} is too big a number for me. Try somewhere below 1000!`, ephemeral: true });
|
await interaction.reply({ content: `Big roller! Unfortunatly ${maxRoll} is too big a number for me. Try somewhere below 1000!`, ephemeral: true });
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
// Prevent 0 or less numbers
|
// Prevent 0 or less numbers
|
||||||
else if (maxRoll < 1) {
|
else if (maxRoll < 1) {
|
||||||
await interaction.reply({ content: `The fewer numbers, the higher the odds! Unfortunatly ${maxRoll} is too low a number... Try a positive number under 1000!`, ephemeral:true });
|
await interaction.reply({ content: `The fewer numbers, the higher the odds! Unfortunatly ${maxRoll} is too low a number... Try a positive number under 1000!`, ephemeral:true });
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
// Limit numbers rollable to prevent spam and API issues
|
// Limit numbers rollable to prevent spam and API issues
|
||||||
if (rollCount > 9) {
|
if (rollCount > 9) {
|
||||||
await interaction.reply({ content: `You want ${rollCount} numbers?! That's a bit much, even for me...\nTry 9 or less please!`, ephemeral: true });
|
await interaction.reply({ content: `You want ${rollCount} numbers?! That's a bit much, even for me...\nTry 9 or less please!`, ephemeral: true });
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
// Prevent 0 or less numbers
|
// Prevent 0 or less numbers
|
||||||
else if (rollCount < 1) {
|
else if (rollCount < 1) {
|
||||||
await interaction.reply({ content: `It's kinda difficult to roll ${rollCount} numbers...\nTry a positive single digit number!`, ephemeral:true });
|
await interaction.reply({ content: `It's kinda difficult to roll ${rollCount} numbers...\nTry a positive single digit number!`, ephemeral:true });
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
const lotteryNumbers = [];
|
const lotteryNumbers = [];
|
||||||
|
|
||||||
for (let i = 0; i < rollCount; i++) {
|
for (let i = 0; i < rollCount; i++) {
|
||||||
lotteryNumbers.push(randomInt(1, maxRoll));
|
lotteryNumbers.push(randomInt(1, maxRoll));
|
||||||
}
|
}
|
||||||
|
|
||||||
if (rollCount === 1) {
|
if (rollCount === 1) {
|
||||||
await interaction.reply({ content: `Your lucky number is...\n${lotteryNumbers.toString().split(',').join(', ')}.`, ephemeral: (isEphemeral === 'true') });
|
await interaction.reply({ content: `Your lucky number is...\n${lotteryNumbers.toString().split(',').join(', ')}.`, ephemeral: (isEphemeral === 'true') });
|
||||||
}
|
}
|
||||||
else {
|
else {
|
||||||
await interaction.reply({ content: `Your lucky numbers are...\n${lotteryNumbers.toString().split(',').join(', ')}.`, ephemeral: (isEphemeral === 'true') });
|
await interaction.reply({ content: `Your lucky numbers are...\n${lotteryNumbers.toString().split(',').join(', ')}.`, ephemeral: (isEphemeral === 'true') });
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
};
|
};
|
|
@ -8,10 +8,10 @@
|
||||||
const { SlashCommandBuilder } = require('discord.js');
|
const { SlashCommandBuilder } = require('discord.js');
|
||||||
|
|
||||||
module.exports = {
|
module.exports = {
|
||||||
data: new SlashCommandBuilder()
|
data: new SlashCommandBuilder()
|
||||||
.setName('ping')
|
.setName('ping')
|
||||||
.setDescription('Checks to see if the bot is online, as well as it\'s ping'),
|
.setDescription('Checks to see if the bot is online, as well as it\'s ping'),
|
||||||
async execute(interaction) {
|
async execute(interaction) {
|
||||||
await interaction.reply({ content: `Pong! Current Websocket Heartbeat / ping is ${interaction.client.ws.ping}ms.`, ephemeral: true });
|
await interaction.reply({ content: `Pong! Current Websocket Heartbeat / ping is ${interaction.client.ws.ping}ms.`, ephemeral: true });
|
||||||
},
|
},
|
||||||
};
|
};
|
148
commands/roll.js
148
commands/roll.js
|
@ -7,94 +7,94 @@ const { SlashCommandBuilder } = require('discord.js');
|
||||||
const { randomInt } = require('node:crypto');
|
const { randomInt } = require('node:crypto');
|
||||||
|
|
||||||
module.exports = {
|
module.exports = {
|
||||||
data: new SlashCommandBuilder()
|
data: new SlashCommandBuilder()
|
||||||
.setName('roll')
|
.setName('roll')
|
||||||
.setDescription('Rolls a set of dice')
|
.setDescription('Rolls a set of dice')
|
||||||
|
|
||||||
// Get number of numbers to roll
|
// Get number of numbers to roll
|
||||||
.addNumberOption(option =>
|
.addNumberOption(option =>
|
||||||
option.setName('die')
|
option.setName('die')
|
||||||
.setDescription('Type of dice to roll')
|
.setDescription('Type of dice to roll')
|
||||||
.addChoices(
|
.addChoices(
|
||||||
{ name: 'd4', value: 4 },
|
{ name: 'd4', value: 4 },
|
||||||
{ name: 'd6', value: 6 },
|
{ name: 'd6', value: 6 },
|
||||||
{ name: 'd8', value: 8 },
|
{ name: 'd8', value: 8 },
|
||||||
{ name: 'd10', value: 10 },
|
{ name: 'd10', value: 10 },
|
||||||
{ name: 'd20', value: 20 },
|
{ name: 'd20', value: 20 },
|
||||||
{ name: 'd100', value: 100 },
|
{ name: 'd100', value: 100 },
|
||||||
))
|
))
|
||||||
|
|
||||||
// Get max number to roll
|
// Get max number to roll
|
||||||
.addNumberOption(option =>
|
.addNumberOption(option =>
|
||||||
option.setName('count')
|
option.setName('count')
|
||||||
.setDescription('Amount of dice to roll'),
|
.setDescription('Amount of dice to roll'),
|
||||||
)
|
)
|
||||||
|
|
||||||
// Get max number to roll
|
// Get max number to roll
|
||||||
.addNumberOption(option =>
|
.addNumberOption(option =>
|
||||||
option.setName('modifier')
|
option.setName('modifier')
|
||||||
.setDescription('+/- to a dice roll'),
|
.setDescription('+/- to a dice roll'),
|
||||||
)
|
)
|
||||||
|
|
||||||
// Optional Ephemeral check to allow user to choose command results to be shared publicly or private; send to self only if no selection.
|
// Optional Ephemeral check to allow user to choose command results to be shared publicly or private; send to self only if no selection.
|
||||||
.addStringOption(option =>
|
.addStringOption(option =>
|
||||||
option.setName('ephemeral')
|
option.setName('ephemeral')
|
||||||
.setDescription('Post the avatar in the current channel')
|
.setDescription('Post the avatar in the current channel')
|
||||||
.addChoices(
|
.addChoices(
|
||||||
{ name: 'Send to me only', value: 'true' },
|
{ name: 'Send to me only', value: 'true' },
|
||||||
{ name: 'Send in channel', value: 'false' },
|
{ name: 'Send in channel', value: 'false' },
|
||||||
)),
|
)),
|
||||||
|
|
||||||
async execute(interaction) {
|
async execute(interaction) {
|
||||||
const isEphemeral = interaction.options.getString('ephemeral') ?? 'true';
|
const isEphemeral = interaction.options.getString('ephemeral') ?? 'true';
|
||||||
const rollCount = interaction.options.getNumber('count') ?? 1;
|
const rollCount = interaction.options.getNumber('count') ?? 1;
|
||||||
const dieType = interaction.options.getNumber('die') ?? 6;
|
const dieType = interaction.options.getNumber('die') ?? 6;
|
||||||
const rollMod = interaction.options.getNumber('modifier') ?? 0;
|
const rollMod = interaction.options.getNumber('modifier') ?? 0;
|
||||||
|
|
||||||
let modSign = '';
|
let modSign = '';
|
||||||
let rollModStr = '';
|
let rollModStr = '';
|
||||||
let rollModNota = '';
|
let rollModNota = '';
|
||||||
|
|
||||||
// Limit numbers rollable to prevent spam and API issues
|
// Limit numbers rollable to prevent spam and API issues
|
||||||
if (rollCount > 100) {
|
if (rollCount > 100) {
|
||||||
await interaction.reply({ content: `You want ${rollCount} numbers?! That's a bit much, even for me...\nTry 100 or less please!`, ephemeral: true });
|
await interaction.reply({ content: `You want ${rollCount} numbers?! That's a bit much, even for me...\nTry 100 or less please!`, ephemeral: true });
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
// Prevent 0 or less numbers
|
// Prevent 0 or less numbers
|
||||||
else if (rollCount < 1) {
|
else if (rollCount < 1) {
|
||||||
await interaction.reply({ content: `It's kinda difficult to roll ${rollCount} numbers...\nTry a positive number!`, ephemeral:true });
|
await interaction.reply({ content: `It's kinda difficult to roll ${rollCount} numbers...\nTry a positive number!`, ephemeral:true });
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
const diceRolls = [];
|
const diceRolls = [];
|
||||||
let rollSum = 0;
|
let rollSum = 0;
|
||||||
|
|
||||||
for (let i = 0; i < rollCount; i++) {
|
for (let i = 0; i < rollCount; i++) {
|
||||||
const randomNum = randomInt(1, dieType);
|
const randomNum = randomInt(1, dieType);
|
||||||
|
|
||||||
diceRolls.push(randomNum);
|
diceRolls.push(randomNum);
|
||||||
rollSum += randomNum;
|
rollSum += randomNum;
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
if (rollMod < 0) {
|
if (rollMod < 0) {
|
||||||
modSign = '-';
|
modSign = '-';
|
||||||
}
|
}
|
||||||
else if (rollMod > 0) {
|
else if (rollMod > 0) {
|
||||||
modSign = '+';
|
modSign = '+';
|
||||||
}
|
}
|
||||||
|
|
||||||
if (rollMod != 0) {
|
if (rollMod != 0) {
|
||||||
rollModStr = ' ' + modSign + ' ' + Math.abs(rollMod);
|
rollModStr = ' ' + modSign + ' ' + Math.abs(rollMod);
|
||||||
rollModNota = modSign + Math.abs(rollMod);
|
rollModNota = modSign + Math.abs(rollMod);
|
||||||
}
|
}
|
||||||
|
|
||||||
const diceRollsString = diceRolls.toString().split(',').join(' + ');
|
const diceRollsString = diceRolls.toString().split(',').join(' + ');
|
||||||
|
|
||||||
for (let i = 0; i < rollCount; i++) {
|
for (let i = 0; i < rollCount; i++) {
|
||||||
diceRolls.push(randomInt(1, dieType));
|
diceRolls.push(randomInt(1, dieType));
|
||||||
}
|
}
|
||||||
|
|
||||||
await interaction.reply({ content: `\`${rollCount}d${dieType}${rollModNota}\`\n\`Rolls: ( ${diceRollsString} )${rollModStr} = ${rollSum + rollMod}\``, ephemeral: (isEphemeral === 'true') });
|
await interaction.reply({ content: `\`${rollCount}d${dieType}${rollModNota}\`\n\`Rolls: ( ${diceRollsString} )${rollModStr} = ${rollSum + rollMod}\``, ephemeral: (isEphemeral === 'true') });
|
||||||
},
|
},
|
||||||
};
|
};
|
|
@ -6,56 +6,56 @@
|
||||||
const { SlashCommandBuilder } = require('discord.js');
|
const { SlashCommandBuilder } = require('discord.js');
|
||||||
|
|
||||||
module.exports = {
|
module.exports = {
|
||||||
data: new SlashCommandBuilder()
|
data: new SlashCommandBuilder()
|
||||||
.setName('server-icon')
|
.setName('server-icon')
|
||||||
.setDescription('Shares this servers current icon')
|
.setDescription('Shares this servers current icon')
|
||||||
|
|
||||||
// Optional choice for user to choose icon size; 4096 if no selection.
|
// Optional choice for user to choose icon size; 4096 if no selection.
|
||||||
.addStringOption(option =>
|
.addStringOption(option =>
|
||||||
option.setName('format')
|
option.setName('format')
|
||||||
.setDescription('Select what format you want the output to be')
|
.setDescription('Select what format you want the output to be')
|
||||||
.addChoices(
|
.addChoices(
|
||||||
{ name: 'WebP', value: 'webp' },
|
{ name: 'WebP', value: 'webp' },
|
||||||
{ name: 'PNG', value: 'png' },
|
{ name: 'PNG', value: 'png' },
|
||||||
{ name: 'JPEG', value: 'jpg' },
|
{ name: 'JPEG', value: 'jpg' },
|
||||||
))
|
))
|
||||||
|
|
||||||
|
|
||||||
// Optional choice for user to choose icon format; webp if no selection.
|
// Optional choice for user to choose icon format; webp if no selection.
|
||||||
.addStringOption(option =>
|
.addStringOption(option =>
|
||||||
option.setName('size')
|
option.setName('size')
|
||||||
.setDescription('Select what size you want the output to be')
|
.setDescription('Select what size you want the output to be')
|
||||||
.addChoices(
|
.addChoices(
|
||||||
{ name: '4096px', value: '4096' },
|
{ name: '4096px', value: '4096' },
|
||||||
{ name: '2048px', value: '2048' },
|
{ name: '2048px', value: '2048' },
|
||||||
{ name: '1024px', value: '1024' },
|
{ name: '1024px', value: '1024' },
|
||||||
{ name: '600px', value: '600' },
|
{ name: '600px', value: '600' },
|
||||||
{ name: '512px', value: '512' },
|
{ name: '512px', value: '512' },
|
||||||
{ name: '300px', value: '300' },
|
{ name: '300px', value: '300' },
|
||||||
{ name: '256px', value: '256' },
|
{ name: '256px', value: '256' },
|
||||||
{ name: '128px', value: '128' },
|
{ name: '128px', value: '128' },
|
||||||
{ name: '96px', value: '96' },
|
{ name: '96px', value: '96' },
|
||||||
{ name: '64px', value: '64' },
|
{ name: '64px', value: '64' },
|
||||||
{ name: '56px', value: '56' },
|
{ name: '56px', value: '56' },
|
||||||
{ name: '32px', value: '32' },
|
{ name: '32px', value: '32' },
|
||||||
{ name: '16px', value: '16' },
|
{ name: '16px', value: '16' },
|
||||||
))
|
))
|
||||||
|
|
||||||
|
|
||||||
// Optional Ephemeral check to allow user to choose command results to be shared publicly or private; send to self only if no selection.
|
// Optional Ephemeral check to allow user to choose command results to be shared publicly or private; send to self only if no selection.
|
||||||
.addStringOption(option =>
|
.addStringOption(option =>
|
||||||
option.setName('ephemeral')
|
option.setName('ephemeral')
|
||||||
.setDescription('Post the icon in the current channel')
|
.setDescription('Post the icon in the current channel')
|
||||||
.addChoices(
|
.addChoices(
|
||||||
{ name: 'Send to me only', value: 'true' },
|
{ name: 'Send to me only', value: 'true' },
|
||||||
{ name: 'Send in channel', value: 'false' },
|
{ name: 'Send in channel', value: 'false' },
|
||||||
)),
|
)),
|
||||||
|
|
||||||
async execute(interaction) {
|
async execute(interaction) {
|
||||||
const iconFormat = interaction.options.getString('format') ?? 'webp';
|
const iconFormat = interaction.options.getString('format') ?? 'webp';
|
||||||
const iconSize = Number(interaction.options.getString('size')) ?? 4096;
|
const iconSize = Number(interaction.options.getString('size')) ?? 4096;
|
||||||
const isEphemeral = interaction.options.getString('ephemeral') ?? 'true';
|
const isEphemeral = interaction.options.getString('ephemeral') ?? 'true';
|
||||||
|
|
||||||
await interaction.reply({ content: `${interaction.guild.iconURL({ extension:iconFormat, size:iconSize, forceStatic:false })}`, ephemeral: (isEphemeral === 'true') });
|
await interaction.reply({ content: `${interaction.guild.iconURL({ extension:iconFormat, size:iconSize, forceStatic:false })}`, ephemeral: (isEphemeral === 'true') });
|
||||||
},
|
},
|
||||||
};
|
};
|
|
@ -14,17 +14,17 @@ const rest = new REST({ version: '10' }).setToken(token);
|
||||||
|
|
||||||
// and deploy your commands!
|
// and deploy your commands!
|
||||||
(async () => {
|
(async () => {
|
||||||
try {
|
try {
|
||||||
console.log('Started deleting all application (/) commands.');
|
console.log('Started deleting all application (/) commands.');
|
||||||
|
|
||||||
// The put method is used to fully refresh all commands
|
// The put method is used to fully refresh all commands
|
||||||
rest.put(Routes.applicationCommands(clientId), { body: [] })
|
rest.put(Routes.applicationCommands(clientId), { body: [] })
|
||||||
.then(() => console.log('Successfully deleted all application (/) commands.'))
|
.then(() => console.log('Successfully deleted all application (/) commands.'))
|
||||||
.catch(console.error);
|
.catch(console.error);
|
||||||
|
|
||||||
}
|
}
|
||||||
catch (error) {
|
catch (error) {
|
||||||
// And of course, make sure you catch and log any errors!
|
// And of course, make sure you catch and log any errors!
|
||||||
console.error(error);
|
console.error(error);
|
||||||
}
|
}
|
||||||
})();
|
})();
|
|
@ -17,9 +17,9 @@ const commandFiles = fs.readdirSync('./commands').filter(file => file.endsWith('
|
||||||
|
|
||||||
// Grab the SlashCommandBuilder#toJSON() output of each command's data for deployment
|
// Grab the SlashCommandBuilder#toJSON() output of each command's data for deployment
|
||||||
for (const file of commandFiles) {
|
for (const file of commandFiles) {
|
||||||
const command = require(`./commands/${file}`);
|
const command = require(`./commands/${file}`);
|
||||||
commands.push(command.data.toJSON());
|
commands.push(command.data.toJSON());
|
||||||
commandsHelp.push(command.data);
|
commandsHelp.push(command.data);
|
||||||
}
|
}
|
||||||
|
|
||||||
// Construct and prepare an instance of the REST module
|
// Construct and prepare an instance of the REST module
|
||||||
|
@ -27,85 +27,85 @@ const rest = new REST({ version: '10' }).setToken(token);
|
||||||
|
|
||||||
// Generate help-text.json
|
// Generate help-text.json
|
||||||
try {
|
try {
|
||||||
console.log(`Generating ${commands.length} help text entries.`);
|
console.log(`Generating ${commands.length} help text entries.`);
|
||||||
|
|
||||||
let helpJSONString = '{\n';
|
let helpJSONString = '{\n';
|
||||||
|
|
||||||
for (let i = 0; i < commandsHelp.length; i++) {
|
for (let i = 0; i < commandsHelp.length; i++) {
|
||||||
helpJSONString += ` "${commandsHelp[i].name}": {\n`;
|
helpJSONString += ` "${commandsHelp[i].name}": {\n`;
|
||||||
helpJSONString += ` "description": "${commandsHelp[i].description}",\n`;
|
helpJSONString += ` "description": "${commandsHelp[i].description}",\n`;
|
||||||
helpJSONString += ' "options": {\n';
|
helpJSONString += ' "options": {\n';
|
||||||
|
|
||||||
for (let j = 0; j < commandsHelp[i].options.length; j++) {
|
for (let j = 0; j < commandsHelp[i].options.length; j++) {
|
||||||
|
|
||||||
helpJSONString += ` "${commandsHelp[i].options[j].name}": {\n`;
|
helpJSONString += ` "${commandsHelp[i].options[j].name}": {\n`;
|
||||||
helpJSONString += ` "description": "${commandsHelp[i].options[j].description}",\n`;
|
helpJSONString += ` "description": "${commandsHelp[i].options[j].description}",\n`;
|
||||||
helpJSONString += ` "required": "${commandsHelp[i].options[j].required}",\n`;
|
helpJSONString += ` "required": "${commandsHelp[i].options[j].required}",\n`;
|
||||||
helpJSONString += ' "choices": {\n';
|
helpJSONString += ' "choices": {\n';
|
||||||
|
|
||||||
if (typeof commandsHelp[i].options[j].choices !== 'undefined') {
|
if (typeof commandsHelp[i].options[j].choices !== 'undefined') {
|
||||||
for (let k = 0; k < commandsHelp[i].options[j].choices.length; k++) {
|
for (let k = 0; k < commandsHelp[i].options[j].choices.length; k++) {
|
||||||
|
|
||||||
helpJSONString += ` "${commandsHelp[i].options[j].choices[k].name}": {\n`;
|
helpJSONString += ` "${commandsHelp[i].options[j].choices[k].name}": {\n`;
|
||||||
helpJSONString += ` "value": "${commandsHelp[i].options[j].choices[k].value}",\n`;
|
helpJSONString += ` "value": "${commandsHelp[i].options[j].choices[k].value}",\n`;
|
||||||
helpJSONString += ' },\n';
|
helpJSONString += ' },\n';
|
||||||
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
helpJSONString += ' },\n';
|
helpJSONString += ' },\n';
|
||||||
helpJSONString += ' },\n';
|
helpJSONString += ' },\n';
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
helpJSONString += ' },\n';
|
helpJSONString += ' },\n';
|
||||||
helpJSONString += ' },\n';
|
helpJSONString += ' },\n';
|
||||||
}
|
}
|
||||||
|
|
||||||
helpJSONString += '}';
|
helpJSONString += '}';
|
||||||
|
|
||||||
// Lazy way out of removing trailing commas
|
// Lazy way out of removing trailing commas
|
||||||
// See https://stackoverflow.com/a/34347475
|
// See https://stackoverflow.com/a/34347475
|
||||||
const helpJSON = JSON.stringify(JSON.parse(helpJSONString.replace(/,(?!\s*?[{["'\w])/g, '')), null, 4);
|
const helpJSON = JSON.stringify(JSON.parse(helpJSONString.replace(/,(?!\s*?[{["'\w])/g, '')), null, 4);
|
||||||
|
|
||||||
// Create data folder if it doesn't exist
|
// Create data folder if it doesn't exist
|
||||||
if (!fs.existsSync('data')) {
|
if (!fs.existsSync('data')) {
|
||||||
fs.mkdirSync('data');
|
fs.mkdirSync('data');
|
||||||
}
|
}
|
||||||
|
|
||||||
// Write file to disk
|
// Write file to disk
|
||||||
fs.writeFile('./data/help-text.json', helpJSON, err => {
|
fs.writeFile('./data/help-text.json', helpJSON, err => {
|
||||||
if (err) {
|
if (err) {
|
||||||
console.log(`Unable to write help-text.json: ${err}`);
|
console.log(`Unable to write help-text.json: ${err}`);
|
||||||
console.log('Stopping...');
|
console.log('Stopping...');
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
console.log(`Successfully generated ${commandsHelp.length} help text entries.`);
|
console.log(`Successfully generated ${commandsHelp.length} help text entries.`);
|
||||||
|
|
||||||
console.log();
|
console.log();
|
||||||
|
|
||||||
// Update slash commands on Discord's side
|
// Update slash commands on Discord's side
|
||||||
(async () => {
|
(async () => {
|
||||||
try {
|
try {
|
||||||
console.log(`Started refreshing ${commands.length} application (/) commands.`);
|
console.log(`Started refreshing ${commands.length} application (/) commands.`);
|
||||||
|
|
||||||
// The put method is used to fully refresh all commands
|
// The put method is used to fully refresh all commands
|
||||||
const data = await rest.put(
|
const data = await rest.put(
|
||||||
Routes.applicationCommands(clientId),
|
Routes.applicationCommands(clientId),
|
||||||
{ body: commands },
|
{ body: commands },
|
||||||
);
|
);
|
||||||
|
|
||||||
console.log(`Successfully reloaded ${data.length} application (/) commands.`);
|
console.log(`Successfully reloaded ${data.length} application (/) commands.`);
|
||||||
}
|
}
|
||||||
catch (error) {
|
catch (error) {
|
||||||
// And of course, make sure you catch and log any errors!
|
// And of course, make sure you catch and log any errors!
|
||||||
console.error(error);
|
console.error(error);
|
||||||
}
|
}
|
||||||
})();
|
})();
|
||||||
}
|
}
|
||||||
catch (error) {
|
catch (error) {
|
||||||
// And of course, make sure you catch and log any errors!
|
// And of course, make sure you catch and log any errors!
|
||||||
console.error(error);
|
console.error(error);
|
||||||
}
|
}
|
110
index.js
110
index.js
|
@ -28,91 +28,91 @@ const commandsPath = path.join(__dirname, 'commands');
|
||||||
const commandFiles = fs.readdirSync(commandsPath).filter(file => file.endsWith('.js'));
|
const commandFiles = fs.readdirSync(commandsPath).filter(file => file.endsWith('.js'));
|
||||||
|
|
||||||
for (const file of commandFiles) {
|
for (const file of commandFiles) {
|
||||||
const filePath = path.join(commandsPath, file);
|
const filePath = path.join(commandsPath, file);
|
||||||
const command = require(filePath);
|
const command = require(filePath);
|
||||||
// Set a new item in the Collection with the key as the command name and the value as the exported module
|
// Set a new item in the Collection with the key as the command name and the value as the exported module
|
||||||
if ('data' in command && 'execute' in command) {
|
if ('data' in command && 'execute' in command) {
|
||||||
client.commands.set(command.data.name, command);
|
client.commands.set(command.data.name, command);
|
||||||
}
|
}
|
||||||
else {
|
else {
|
||||||
logger.log(logger.logLevels.WARN, `The command at ${filePath} is missing a required "data" or "execute" property.`);
|
logger.log(logger.logLevels.WARN, `The command at ${filePath} is missing a required "data" or "execute" property.`);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// When the client is ready, run this code (only once)
|
// When the client is ready, run this code (only once)
|
||||||
// We use 'c' for the event parameter to keep it separate from the already defined 'client'
|
// We use 'c' for the event parameter to keep it separate from the already defined 'client'
|
||||||
client.once(Events.ClientReady, c => {
|
client.once(Events.ClientReady, c => {
|
||||||
logger.log(logger.logLevels.INFO, `${logger.colorText('Ready!', logger.textColor.Green)} Logged in as ${logger.colorText(c.user.tag, logger.textColor.Blue)}`);
|
logger.log(logger.logLevels.INFO, `${logger.colorText('Ready!', logger.textColor.Green)} Logged in as ${logger.colorText(c.user.tag, logger.textColor.Blue)}`);
|
||||||
client.user.setPresence({ activities: [{ name: activity }], status: status });
|
client.user.setPresence({ activities: [{ name: activity }], status: status });
|
||||||
|
|
||||||
// Track websocket heartbeat with PM2 Histogram
|
// Track websocket heartbeat with PM2 Histogram
|
||||||
let latency = 0;
|
let latency = 0;
|
||||||
setInterval(function() {
|
setInterval(function() {
|
||||||
latency = c.ws.ping;
|
latency = c.ws.ping;
|
||||||
metrics.websocketHeartbeatHist.update(latency);
|
metrics.websocketHeartbeatHist.update(latency);
|
||||||
}, 1000);
|
}, 1000);
|
||||||
|
|
||||||
// Report current server count with PM2 (Servers counted anonymously)
|
// Report current server count with PM2 (Servers counted anonymously)
|
||||||
metrics.serverCount.set(c.guilds.cache.size);
|
metrics.serverCount.set(c.guilds.cache.size);
|
||||||
|
|
||||||
});
|
});
|
||||||
|
|
||||||
// Client "on" Events
|
// Client "on" Events
|
||||||
// Someone used an interaction
|
// Someone used an interaction
|
||||||
client.on(Events.InteractionCreate, async interaction => {
|
client.on(Events.InteractionCreate, async interaction => {
|
||||||
if (!interaction.isChatInputCommand()) return;
|
if (!interaction.isChatInputCommand()) return;
|
||||||
|
|
||||||
const command = interaction.client.commands.get(interaction.commandName);
|
const command = interaction.client.commands.get(interaction.commandName);
|
||||||
|
|
||||||
if (!command) {
|
if (!command) {
|
||||||
logger.log(logger.logLevels.ERROR, `No command matching ${interaction.commandName} was found.`);
|
logger.log(logger.logLevels.ERROR, `No command matching ${interaction.commandName} was found.`);
|
||||||
await interaction.reply({ content: `This command no longer exists! Please contact ${botOwner} to report that this is happening!`, ephemeral: true });
|
await interaction.reply({ content: `This command no longer exists! Please contact ${botOwner} to report that this is happening!`, ephemeral: true });
|
||||||
|
|
||||||
// Report error to PM2 dashboard
|
// Report error to PM2 dashboard
|
||||||
metrics.interactionErrors.inc();
|
metrics.interactionErrors.inc();
|
||||||
metrics.io.notifyError(new Error('Interaction doesn\'t exist'), {
|
metrics.io.notifyError(new Error('Interaction doesn\'t exist'), {
|
||||||
custom: {
|
custom: {
|
||||||
interactionCommand: interaction.commandName,
|
interactionCommand: interaction.commandName,
|
||||||
},
|
},
|
||||||
});
|
});
|
||||||
|
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
try {
|
try {
|
||||||
await command.execute(interaction);
|
await command.execute(interaction);
|
||||||
}
|
}
|
||||||
catch (error) {
|
catch (error) {
|
||||||
logger.log(logger.logLevels.ERROR, error);
|
logger.log(logger.logLevels.ERROR, error);
|
||||||
await interaction.reply({ content: 'There was an error while executing this command!', ephemeral: true });
|
await interaction.reply({ content: 'There was an error while executing this command!', ephemeral: true });
|
||||||
|
|
||||||
// Report error to PM2 dashboard
|
// Report error to PM2 dashboard
|
||||||
metrics.interactionErrors.inc();
|
metrics.interactionErrors.inc();
|
||||||
metrics.io.notifyError(new Error('Error executing interaction'), {
|
metrics.io.notifyError(new Error('Error executing interaction'), {
|
||||||
custom: {
|
custom: {
|
||||||
interactionCommand: interaction.commandName,
|
interactionCommand: interaction.commandName,
|
||||||
error: error,
|
error: error,
|
||||||
},
|
},
|
||||||
});
|
});
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
// Successful Execution, report as a PM2 metric
|
// Successful Execution, report as a PM2 metric
|
||||||
// If the bot gets a lot of use, consider removing this for performance
|
// If the bot gets a lot of use, consider removing this for performance
|
||||||
metrics.interactionSuccess();
|
metrics.interactionSuccess();
|
||||||
|
|
||||||
});
|
});
|
||||||
|
|
||||||
// Joined a server
|
// Joined a server
|
||||||
client.on(Events.GuildCreate, guild => {
|
client.on(Events.GuildCreate, guild => {
|
||||||
// Report current server count with PM2 (Servers counted anonymously)
|
// Report current server count with PM2 (Servers counted anonymously)
|
||||||
metrics.serverCount.set(guild.client.guilds.cache.size);
|
metrics.serverCount.set(guild.client.guilds.cache.size);
|
||||||
});
|
});
|
||||||
|
|
||||||
// Removed from a server
|
// Removed from a server
|
||||||
client.on(Events.GuildDelete, guild => {
|
client.on(Events.GuildDelete, guild => {
|
||||||
// Report current server count with PM2 (Servers counted anonymously)
|
// Report current server count with PM2 (Servers counted anonymously)
|
||||||
metrics.serverCount.set(guild.client.guilds.cache.size);
|
metrics.serverCount.set(guild.client.guilds.cache.size);
|
||||||
});
|
});
|
||||||
|
|
||||||
// Log in to Discord with your client's token
|
// Log in to Discord with your client's token
|
||||||
|
|
Loading…
Reference in a new issue