Initial setup for standard events
This commit is contained in:
parent
460a7ed557
commit
3e6168a396
|
@ -2,3 +2,4 @@ config.ts
|
||||||
logs
|
logs
|
||||||
|
|
||||||
db/update.ts
|
db/update.ts
|
||||||
|
deno.lock
|
||||||
|
|
|
@ -2,7 +2,7 @@ export const config = {
|
||||||
'name': 'Group Up', // Name of the bot
|
'name': 'Group Up', // Name of the bot
|
||||||
'version': '1.0.0', // Version of the bot
|
'version': '1.0.0', // Version of the bot
|
||||||
'token': 'the_bot_token', // Discord API Token for this bot
|
'token': 'the_bot_token', // Discord API Token for this bot
|
||||||
'localtoken': 'local_testing_token', // Discord API Token for a secondary OPTIONAL testing bot, THIS MUST BE DIFFERENT FROM "token"
|
'localToken': 'local_testing_token', // Discord API Token for a secondary OPTIONAL testing bot, THIS MUST BE DIFFERENT FROM "token"
|
||||||
'prefix': 'gu!', // Prefix for all commands
|
'prefix': 'gu!', // Prefix for all commands
|
||||||
'db': { // Settings for the MySQL database, this is required for use with the API, if you do not want to set this up, you will need to rip all code relating to the DB out of the bot
|
'db': { // Settings for the MySQL database, this is required for use with the API, if you do not want to set this up, you will need to rip all code relating to the DB out of the bot
|
||||||
'host': '', // IP address for the db, usually localhost
|
'host': '', // IP address for the db, usually localhost
|
||||||
|
|
46
deps.ts
46
deps.ts
|
@ -1,40 +1,14 @@
|
||||||
// All external dependancies are to be loaded here to make updating dependancy versions much easier
|
// All external dependencies are to be loaded here to make updating dependency versions much easier
|
||||||
export {
|
import { getBotIdFromToken } from 'https://deno.land/x/discordeno@16.0.1/mod.ts';
|
||||||
botId,
|
import config from './config.ts';
|
||||||
cache,
|
import { LOCALMODE } from './flags.ts';
|
||||||
cacheHandlers,
|
export const botId = getBotIdFromToken(LOCALMODE ? config.localToken : config.token);
|
||||||
deleteMessage,
|
|
||||||
DiscordActivityTypes,
|
|
||||||
DiscordButtonStyles,
|
|
||||||
DiscordInteractionResponseTypes,
|
|
||||||
DiscordInteractionTypes,
|
|
||||||
editBotNickname,
|
|
||||||
editBotStatus,
|
|
||||||
getGuild,
|
|
||||||
getMessage,
|
|
||||||
getUser,
|
|
||||||
hasGuildPermissions,
|
|
||||||
Intents,
|
|
||||||
sendDirectMessage,
|
|
||||||
sendInteractionResponse,
|
|
||||||
sendMessage,
|
|
||||||
startBot,
|
|
||||||
structures,
|
|
||||||
} from 'https://deno.land/x/discordeno@17.0.1/mod.ts';
|
|
||||||
|
|
||||||
export type {
|
export { enableCachePlugin, enableCacheSweepers } from 'https://deno.land/x/discordeno@17.0.1/plugins/cache/mod.ts';
|
||||||
ActionRow,
|
export type { BotWithCache } from 'https://deno.land/x/discordeno@17.0.1/plugins/cache/mod.ts';
|
||||||
ButtonComponent,
|
|
||||||
ButtonData,
|
export { ActivityTypes, createBot, editBotMember, editBotStatus, getBotIdFromToken, Intents, sendInteractionResponse, sendMessage, startBot } from 'https://deno.land/x/discordeno@17.0.1/mod.ts';
|
||||||
CreateMessage,
|
export type { ActionRow, Bot, ButtonComponent, CreateMessage, Embed, EventHandlers, Guild, Interaction, Message } from 'https://deno.land/x/discordeno@17.0.1/mod.ts';
|
||||||
DebugArg,
|
|
||||||
DiscordenoGuild,
|
|
||||||
DiscordenoMember,
|
|
||||||
DiscordenoMessage,
|
|
||||||
Embed,
|
|
||||||
EmbedField,
|
|
||||||
Interaction,
|
|
||||||
} from 'https://deno.land/x/discordeno@17.0.1/mod.ts';
|
|
||||||
|
|
||||||
export { Client } from 'https://deno.land/x/mysql@v2.11.0/mod.ts';
|
export { Client } from 'https://deno.land/x/mysql@v2.11.0/mod.ts';
|
||||||
|
|
||||||
|
|
18
mod.ts
18
mod.ts
|
@ -0,0 +1,18 @@
|
||||||
|
import config from './config.ts';
|
||||||
|
import { DEBUG, LOCALMODE } from './flags.ts';
|
||||||
|
import { createBot, enableCachePlugin, enableCacheSweepers, initLog, Intents, startBot } from './deps.ts';
|
||||||
|
import { events } from './src/events.ts';
|
||||||
|
|
||||||
|
// Initialize logging client with folder to use for logs, needs --allow-write set on Deno startup
|
||||||
|
initLog('logs', DEBUG);
|
||||||
|
|
||||||
|
// Set up the Discord Bot
|
||||||
|
const bot = enableCachePlugin(createBot({
|
||||||
|
token: LOCALMODE ? config.localToken : config.token,
|
||||||
|
intents: Intents.MessageContent | Intents.GuildMessages | Intents.DirectMessages | Intents.Guilds | Intents.GuildMessageReactions,
|
||||||
|
events,
|
||||||
|
}));
|
||||||
|
enableCacheSweepers(bot);
|
||||||
|
|
||||||
|
// Start the bot
|
||||||
|
startBot(bot);
|
|
@ -0,0 +1,30 @@
|
||||||
|
import config from '../config.ts';
|
||||||
|
|
||||||
|
export const failColor = 0xe71212;
|
||||||
|
export const warnColor = 0xe38f28;
|
||||||
|
export const successColor = 0x0f8108;
|
||||||
|
export const infoColor1 = 0x313bf9;
|
||||||
|
export const infoColor2 = 0x6805e9;
|
||||||
|
|
||||||
|
export const getRandomStatus = (guildCount: number): string => {
|
||||||
|
let status = '';
|
||||||
|
switch (Math.floor((Math.random() * 5) + 1)) {
|
||||||
|
case 1:
|
||||||
|
status = `${config.prefix}help for commands`;
|
||||||
|
break;
|
||||||
|
case 2:
|
||||||
|
status = `Running V${config.version}`;
|
||||||
|
break;
|
||||||
|
case 3:
|
||||||
|
status = `${config.prefix}info to learn more`;
|
||||||
|
break;
|
||||||
|
case 4:
|
||||||
|
status = 'Mention me to check my prefix!';
|
||||||
|
break;
|
||||||
|
default:
|
||||||
|
status = `Running LFGs in ${guildCount} servers`;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
|
||||||
|
return status;
|
||||||
|
};
|
|
@ -0,0 +1,15 @@
|
||||||
|
import config from '../config.ts';
|
||||||
|
import { Client } from '../deps.ts';
|
||||||
|
import { LOCALMODE } from '../flags.ts';
|
||||||
|
|
||||||
|
export const dbClient = await new Client().connect({
|
||||||
|
hostname: LOCALMODE ? config.db.localhost : config.db.host,
|
||||||
|
port: config.db.port,
|
||||||
|
db: config.db.name,
|
||||||
|
username: config.db.username,
|
||||||
|
password: config.db.password,
|
||||||
|
});
|
||||||
|
|
||||||
|
export const queries = {
|
||||||
|
callIncCnt: (cmdName: string) => `CALL INC_CNT("${cmdName}");`,
|
||||||
|
};
|
|
@ -0,0 +1,17 @@
|
||||||
|
import { DEVMODE } from '../flags.ts';
|
||||||
|
import {
|
||||||
|
// Discordeno deps
|
||||||
|
EventHandlers,
|
||||||
|
} from '../deps.ts';
|
||||||
|
import eventHandlers from './events/_index.ts';
|
||||||
|
|
||||||
|
export const events: Partial<EventHandlers> = {};
|
||||||
|
|
||||||
|
events.ready = eventHandlers.ready;
|
||||||
|
events.guildCreate = eventHandlers.guildCreate;
|
||||||
|
events.guildDelete = eventHandlers.guildDelete;
|
||||||
|
events.messageCreate = eventHandlers.messageCreate;
|
||||||
|
|
||||||
|
if (DEVMODE) {
|
||||||
|
events.debug = eventHandlers.debug;
|
||||||
|
}
|
|
@ -0,0 +1,13 @@
|
||||||
|
import { ready } from './ready.ts';
|
||||||
|
import { guildCreate } from './guildCreate.ts';
|
||||||
|
import { guildDelete } from './guildDelete.ts';
|
||||||
|
import { debug } from './debug.ts';
|
||||||
|
import { messageCreate } from './messageCreate.ts';
|
||||||
|
|
||||||
|
export default {
|
||||||
|
ready,
|
||||||
|
guildCreate,
|
||||||
|
guildDelete,
|
||||||
|
debug,
|
||||||
|
messageCreate,
|
||||||
|
};
|
|
@ -0,0 +1,8 @@
|
||||||
|
import {
|
||||||
|
// Log4Deno deps
|
||||||
|
log,
|
||||||
|
LT,
|
||||||
|
} from '../../deps.ts';
|
||||||
|
import utils from '../utils.ts';
|
||||||
|
|
||||||
|
export const debug = (dmsg: string) => log(LT.LOG, `Debug Message | ${utils.jsonStringifyBig(dmsg)}`);
|
|
@ -0,0 +1,40 @@
|
||||||
|
import config from '../../config.ts';
|
||||||
|
import {
|
||||||
|
// Discordeno deps
|
||||||
|
Bot,
|
||||||
|
Guild,
|
||||||
|
// Log4Deno deps
|
||||||
|
log,
|
||||||
|
LT,
|
||||||
|
// Discordeno deps
|
||||||
|
sendMessage,
|
||||||
|
} from '../../deps.ts';
|
||||||
|
import { infoColor1 } from '../commandUtils.ts';
|
||||||
|
import utils from '../utils.ts';
|
||||||
|
|
||||||
|
export const guildCreate = (bot: Bot, guild: Guild) => {
|
||||||
|
log(LT.LOG, `Handling joining guild ${utils.jsonStringifyBig(guild)}`);
|
||||||
|
sendMessage(bot, config.logChannel, {
|
||||||
|
embeds: [{
|
||||||
|
title: 'Guild Joined!',
|
||||||
|
color: infoColor1,
|
||||||
|
fields: [
|
||||||
|
{
|
||||||
|
name: 'Name:',
|
||||||
|
value: `${guild.name}`,
|
||||||
|
inline: true,
|
||||||
|
},
|
||||||
|
{
|
||||||
|
name: 'Id:',
|
||||||
|
value: `${guild.id}`,
|
||||||
|
inline: true,
|
||||||
|
},
|
||||||
|
{
|
||||||
|
name: 'Member Count:',
|
||||||
|
value: `${guild.memberCount}`,
|
||||||
|
inline: true,
|
||||||
|
},
|
||||||
|
],
|
||||||
|
}],
|
||||||
|
}).catch((e: Error) => utils.commonLoggers.messageSendError('mod.ts:95', 'Join Guild', e));
|
||||||
|
};
|
|
@ -0,0 +1,39 @@
|
||||||
|
import config from '../../config.ts';
|
||||||
|
import {
|
||||||
|
// Discordeno deps
|
||||||
|
Bot,
|
||||||
|
// Log4Deno deps
|
||||||
|
log,
|
||||||
|
LT,
|
||||||
|
// Discordeno deps
|
||||||
|
sendMessage,
|
||||||
|
} from '../../deps.ts';
|
||||||
|
import { warnColor } from '../commandUtils.ts';
|
||||||
|
import { dbClient } from '../db.ts';
|
||||||
|
import utils from '../utils.ts';
|
||||||
|
|
||||||
|
export const guildDelete = async (bot: Bot, guildId: bigint) => {
|
||||||
|
log(LT.LOG, `Handling leaving guild ${utils.jsonStringifyBig(guildId)}`);
|
||||||
|
|
||||||
|
try {
|
||||||
|
await dbClient.execute('DELETE FROM guild_prefix WHERE guildId = ?', [guildId]);
|
||||||
|
await dbClient.execute('DELETE FROM guild_mod_role WHERE guildId = ?', [guildId]);
|
||||||
|
await dbClient.execute('DELETE FROM guild_clean_channel WHERE guildId = ?', [guildId]);
|
||||||
|
} catch (e) {
|
||||||
|
log(LT.WARN, `Failed to remove guild from DB: ${utils.jsonStringifyBig(e)}`);
|
||||||
|
}
|
||||||
|
|
||||||
|
sendMessage(bot, config.logChannel, {
|
||||||
|
embeds: [{
|
||||||
|
title: 'Removed from Guild',
|
||||||
|
color: warnColor,
|
||||||
|
fields: [
|
||||||
|
{
|
||||||
|
name: 'Id:',
|
||||||
|
value: `${guildId}`,
|
||||||
|
inline: true,
|
||||||
|
},
|
||||||
|
],
|
||||||
|
}],
|
||||||
|
}).catch((e: Error) => utils.commonLoggers.messageSendError('guildDelete.ts:28', 'Leave Guild', e));
|
||||||
|
};
|
|
@ -0,0 +1,17 @@
|
||||||
|
import config from '../../config.ts';
|
||||||
|
import { Bot, botId, Message } from '../../deps.ts';
|
||||||
|
|
||||||
|
export const messageCreate = async (bot: Bot, message: Message) => {
|
||||||
|
// Ignore all messages that are not commands
|
||||||
|
if (message.content.indexOf(config.prefix) !== 0) {
|
||||||
|
// Handle @bot messages
|
||||||
|
if (message.mentionedUserIds[0] === botId && (message.content.trim().startsWith(`<@${botId}>`) || message.content.trim().startsWith(`<@!${botId}>`))) {
|
||||||
|
}
|
||||||
|
|
||||||
|
// return as we are done handling this command
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Ignore all other bots
|
||||||
|
if (message.isFromBot) return;
|
||||||
|
};
|
|
@ -0,0 +1,62 @@
|
||||||
|
import config from '../../config.ts';
|
||||||
|
import { LOCALMODE } from '../../flags.ts';
|
||||||
|
import { ActivityTypes, Bot, BotWithCache, editBotMember, editBotStatus, log, LT, sendMessage } from '../../deps.ts';
|
||||||
|
import { getRandomStatus, successColor } from '../commandUtils.ts';
|
||||||
|
import utils from '../utils.ts';
|
||||||
|
|
||||||
|
export const ready = (rawBot: Bot) => {
|
||||||
|
const bot = rawBot as BotWithCache;
|
||||||
|
log(LT.INFO, `${config.name} Logged in!`);
|
||||||
|
editBotStatus(bot, {
|
||||||
|
activities: [{
|
||||||
|
name: 'Booting up . . .',
|
||||||
|
type: ActivityTypes.Game,
|
||||||
|
createdAt: new Date().getTime(),
|
||||||
|
}],
|
||||||
|
status: 'online',
|
||||||
|
});
|
||||||
|
|
||||||
|
// Interval to rotate the status text every 30 seconds to show off more commands
|
||||||
|
setInterval(async () => {
|
||||||
|
log(LT.LOG, 'Changing bot status');
|
||||||
|
try {
|
||||||
|
// Wrapped in try-catch due to hard crash possible
|
||||||
|
editBotStatus(bot, {
|
||||||
|
activities: [{
|
||||||
|
name: getRandomStatus(bot.guilds.size + bot.dispatchedGuildIds.size),
|
||||||
|
type: ActivityTypes.Game,
|
||||||
|
createdAt: new Date().getTime(),
|
||||||
|
}],
|
||||||
|
status: 'online',
|
||||||
|
});
|
||||||
|
} catch (e) {
|
||||||
|
log(LT.ERROR, `Failed to update status: ${utils.jsonStringifyBig(e)}`);
|
||||||
|
}
|
||||||
|
}, 30000);
|
||||||
|
|
||||||
|
// setTimeout added to make sure the startup message does not error out
|
||||||
|
setTimeout(() => {
|
||||||
|
LOCALMODE && editBotMember(bot, config.devServer, { nick: `LOCAL - ${config.name}` });
|
||||||
|
editBotStatus(bot, {
|
||||||
|
activities: [{
|
||||||
|
name: 'Booting Complete',
|
||||||
|
type: ActivityTypes.Game,
|
||||||
|
createdAt: new Date().getTime(),
|
||||||
|
}],
|
||||||
|
status: 'online',
|
||||||
|
});
|
||||||
|
sendMessage(bot, config.logChannel, {
|
||||||
|
embeds: [{
|
||||||
|
title: `${config.name} is now Online`,
|
||||||
|
color: successColor,
|
||||||
|
fields: [
|
||||||
|
{
|
||||||
|
name: 'Version:',
|
||||||
|
value: `${config.version}`,
|
||||||
|
inline: true,
|
||||||
|
},
|
||||||
|
],
|
||||||
|
}],
|
||||||
|
}).catch((e: Error) => utils.commonLoggers.messageSendError('ready.ts:71', 'Startup', e));
|
||||||
|
}, 1000);
|
||||||
|
};
|
|
@ -0,0 +1,39 @@
|
||||||
|
import {
|
||||||
|
// Log4Deno deps
|
||||||
|
log,
|
||||||
|
LT,
|
||||||
|
// Discordeno deps
|
||||||
|
Message,
|
||||||
|
} from '../deps.ts';
|
||||||
|
|
||||||
|
const jsonStringifyBig = (input: any) => {
|
||||||
|
return JSON.stringify(input, (_key, value) => typeof value === 'bigint' ? value.toString() + 'n' : value);
|
||||||
|
};
|
||||||
|
|
||||||
|
const genericLogger = (level: LT, message: string) => log(level, message);
|
||||||
|
const messageEditError = (location: string, message: Message | string, err: Error) =>
|
||||||
|
genericLogger(LT.ERROR, `${location} | Failed to edit message: ${jsonStringifyBig(message)} | Error: ${err.name} - ${err.message}`);
|
||||||
|
const messageGetError = (location: string, message: Message | string, err: Error) =>
|
||||||
|
genericLogger(LT.ERROR, `${location} | Failed to get message: ${jsonStringifyBig(message)} | Error: ${err.name} - ${err.message}`);
|
||||||
|
const messageSendError = (location: string, message: Message | string, err: Error) =>
|
||||||
|
genericLogger(LT.ERROR, `${location} | Failed to send message: ${jsonStringifyBig(message)} | Error: ${err.name} - ${err.message}`);
|
||||||
|
const messageDeleteError = (location: string, message: Message | string, err: Error) =>
|
||||||
|
genericLogger(LT.ERROR, `${location} | Failed to delete message: ${jsonStringifyBig(message)} | Error: ${err.name} - ${err.message}`);
|
||||||
|
const reactionAddError = (location: string, message: Message | string, err: Error, emoji: string) =>
|
||||||
|
genericLogger(LT.ERROR, `${location} | Failed to add emoji (${emoji}) to message: ${jsonStringifyBig(message)} | Error: ${err.name} - ${err.message}`);
|
||||||
|
const reactionDeleteError = (location: string, message: Message | string, err: Error, emoji: string) =>
|
||||||
|
genericLogger(LT.ERROR, `${location} | Failed to delete emoji (${emoji}) from message: ${jsonStringifyBig(message)} | Error: ${err.name} - ${err.message}`);
|
||||||
|
const dbError = (location: string, type: string, err: Error) => genericLogger(LT.ERROR, `${location} | Failed to ${type} database | Error: ${err.name} - ${err.message}`);
|
||||||
|
|
||||||
|
export default {
|
||||||
|
commonLoggers: {
|
||||||
|
dbError,
|
||||||
|
messageGetError,
|
||||||
|
messageEditError,
|
||||||
|
messageSendError,
|
||||||
|
messageDeleteError,
|
||||||
|
reactionAddError,
|
||||||
|
reactionDeleteError,
|
||||||
|
},
|
||||||
|
jsonStringifyBig,
|
||||||
|
};
|
Loading…
Reference in New Issue