import { Sticker, ThreadChannel, Message, User, Invite, GuildMember, GuildScheduledEvent, GuildEmoji, Channel, Client, Events, GuildAuditLogsEntry, AuditLogEvent } from 'discord.js'; import { AuditLog, db } from './db'; import * as log from './log'; export enum EventType { ChannelCreate = 'CHANNEL_CREATE', ChannelRename = 'CHANNEL_RENAME', ChannelDelete = 'CHANNEL_DELETE', EmojiCreate = 'EMOJI_CREATE', EmojiRename = 'EMOJI_RENAME', EmojiDelete = 'EMOJI_DELETE', EventCreate = 'EVENT_CREATE', EventEdit = 'EVENT_EDIT', EventDelete = 'EVENT_DELETE', InviteCreate = 'INVITE_CREATE', InviteUpdate = 'INVITE_UPDATE', InviteDelete = 'INVITE_DELETE', MemberBan = 'MEMBER_BAN', MemberUnban = 'MEMBER_UNBAN', MemberKick = 'MEMBER_KICK', MemberDisconnect = 'MEMBER_DISCONNECT', MemberNickname = 'MEMBER_NICKNAME', MemberChangeRoles = 'MEMBER_CHANGE_ROLES', MessageDelete = 'MESSAGE_DELETE', MessageEdit = 'MESSAGE_EDIT', StickerCreate = 'STICKER_CREATE', StickerRename = 'STICKER_RENAME', StickerDelete = 'STICKER_DELETE', ThreadCreate = 'THREAD_CREATE', ThreadEdit = 'THREAD_EDIT', ThreadDelete = 'THREAD_DELETE', } export type Event = { type: EventType.ChannelCreate, causer: User, channel: Channel, } | { type: EventType.ChannelRename, causer: User, channel: Channel, oldName: string, newName: string, } | { type: EventType.ChannelDelete, causer: User, channel: Channel, } | { type: EventType.EmojiCreate, causer: User, emoji: GuildEmoji, } | { type: EventType.EmojiRename, causer: User, emoji: GuildEmoji, oldName: string, newName: string, } | { type: EventType.EmojiDelete, causer: User, emoji: GuildEmoji, } | { type: EventType.EventCreate, causer: User, event: GuildScheduledEvent, } | { type: EventType.EventEdit, causer: User, oldEvent: GuildScheduledEvent, event: GuildScheduledEvent, } | { type: EventType.EventDelete, causer: User, event: GuildScheduledEvent, } | { type: EventType.InviteCreate, causer: User, invite: Invite, } | { type: EventType.InviteUpdate, causer: User, oldInvite: Invite, invite: Invite, } | { type: EventType.InviteDelete, causer: User, invite: Invite, } | { type: EventType.MemberBan, causer: User, member: GuildMember, reason: string, } | { type: EventType.MemberUnban, causer: User, member: GuildMember, reason: string, } | { type: EventType.MemberKick, causer: User, member: GuildMember, reason: string, } | { type: EventType.MemberDisconnect, causer: User, member: GuildMember, } | { type: EventType.MemberNickname, causer: User, member: GuildMember, oldNickname: string, newNickname: string, } | { type: EventType.MemberChangeRoles, causer: User, member: GuildMember, // TODO: huh } | { type: EventType.MessageDelete, causer: User, message: Message, } | { type: EventType.MessageEdit, causer: User, oldMessage: Message, message: Message, } | { type: EventType.StickerCreate, causer: User, sticker: Sticker, } | { type: EventType.StickerRename, causer: User, oldName: string, newName: string, } | { type: EventType.StickerDelete, causer: User, sticker: Sticker, } | { type: EventType.ThreadCreate, causer: User, thread: ThreadChannel, } | { type: EventType.ThreadEdit, causer: User, oldThread: ThreadChannel, thread: ThreadChannel, } | { type: EventType.ThreadDelete, causer: User, thread: ThreadChannel, }; export async function triggerEvent(bot: Client, event: Event) { const type = event.type; log.info(`Got event ${event.type}: ${JSON.stringify(event)}`); const logs = await db('auditLogs') .select('guild', 'channel') // @ts-expect-error this LITERALLY works .whereLike(db.raw('UPPER(eventTypes)'), `%${type.toUpperCase()}%`); for (const auditLog of logs) { let channel; try { channel = await bot.channels.fetch(auditLog.channel); } catch (err) { log.warn(err); } if (channel && channel.isText()) { channel.send(`${JSON.stringify(event)}`); } else { log.warn(`Channel ${auditLog.channel} from guild ${auditLog.guild} not found! Deleting audit log`); await db('auditLogs') .where('channel', auditLog.channel) .delete(); } } } export function setupListeners(bot: Client) { /*bot.on(Events.GuildAuditLogEntryCreate, async (auditLog: GuildAuditLogsEntry) => { const { action, extra: channel, executorId, targetId } = auditLog; // Check only for deleted messages. if (action !== AuditLogEvent.MessageDelete) return; // Ensure the executor is cached. const executor = await bot.users.fetch(executorId); // Ensure the author whose message was deleted is cached. const target = await bot.users.fetch(targetId); // Log the output. console.log(`A message by ${target.tag} was deleted by ${executor.tag} in ${channel}.`); });*/ }