diff --git a/.DS_Store b/.DS_Store new file mode 100644 index 0000000..3d82699 Binary files /dev/null and b/.DS_Store differ diff --git a/src/.DS_Store b/src/.DS_Store new file mode 100644 index 0000000..9a701be Binary files /dev/null and b/src/.DS_Store differ diff --git a/src/events/guild_member/guildMemberVoiceUpdate.ts b/src/events/guild_member/guildMemberVoiceUpdate.ts index 80633bb..7295df7 100644 --- a/src/events/guild_member/guildMemberVoiceUpdate.ts +++ b/src/events/guild_member/guildMemberVoiceUpdate.ts @@ -89,11 +89,11 @@ export const guildMemberVoiceUpdate = new Event({ } const settings = await GuildSetting.findOne({ guildId: guild.id }); - // check that logging channel ID is set + // Check that logging channel ID is set const loggingChannelId = settings?.logging.voiceUpdatesChannelId; if (!loggingChannelId) return; - // check that logging channel exists in guild + // Check that logging channel exists in guild const loggingChannel = await getGuildChannel(guild, loggingChannelId); if (!loggingChannel?.isSendable()) return; @@ -107,7 +107,7 @@ export const guildMemberVoiceUpdate = new Event({ * @param title - Title for the embed * @param description - description for the embed * @param color - Color for the embed - * @returns embed builder + * @returns - Embed builder */ function vcLogEmbed( member: GuildMember, @@ -125,9 +125,10 @@ function vcLogEmbed( } /** + * Marks member's attendance * - * @param channelId - * @param member + * @param channelId Voice chatroom ID + * @param member Member changing state */ async function markAttendance( channelId: string, @@ -136,6 +137,7 @@ async function markAttendance( ) { try { await dbConnect(); + // Grabing Scheduled Event object by channel ID const res: IScheduledEvent = (await ScheduledEvent.findOne({ channelId: channelId, status: 2, diff --git a/src/events/guild_scheduled_event/guildScheduledEventDelete.ts b/src/events/guild_scheduled_event/guildScheduledEventDelete.ts index 89421c4..e86c0a7 100644 --- a/src/events/guild_scheduled_event/guildScheduledEventDelete.ts +++ b/src/events/guild_scheduled_event/guildScheduledEventDelete.ts @@ -7,16 +7,26 @@ import { } from "../../models/ScheduledEvent.js"; import dbConnect from "../../util/libmongo.js"; +/** + * `guildScheduledEventDelete` + * handles the {@link Events.guildScheduledEventDelete} + * {@link Event}. + * Flags scheduled event as canceled in database. + */ + export const guildScheduledEventDelete = new Event({ name: Events.GuildScheduledEventDelete, execute: async (event) => { console.log("deleting"); await dbConnect(); + // Finds event by ID const res: IScheduledEvent = ( await ScheduledEvent.find({ eventId: event.id }).sort({ _id: -1 }).exec() )[0] as IScheduledEvent; + // Flags event for deletion and then save res.status = GuildScheduledEventStatus.Canceled; res.save(); + // Old record inseted into logs await logScheduledEvent(res); }, }); diff --git a/src/events/guild_scheduled_event/guildScheduledEventUpdate.ts b/src/events/guild_scheduled_event/guildScheduledEventUpdate.ts index 9becb15..0069c75 100644 --- a/src/events/guild_scheduled_event/guildScheduledEventUpdate.ts +++ b/src/events/guild_scheduled_event/guildScheduledEventUpdate.ts @@ -7,6 +7,12 @@ import { } from "../../models/ScheduledEvent.js"; import dbConnect from "../../util/libmongo.js"; +/** + * `guildScheduledEventUpdate` handles the {@link Events.guildScheduledEventUpdate} + * {@link Event}. + * Updates schelude event in database. + */ +// Using the oldEvent and newEvent parameters, the function updates the currently saved oldEvent with newEvent. export const guildScheduledEventUpdate = new Event({ name: Events.GuildScheduledEventUpdate, execute: async (oldEvent, newEvent) => { @@ -17,7 +23,7 @@ export const guildScheduledEventUpdate = new Event({ await dbConnect(); let res; - + // After the update completes, the updated event is logged if (oldEvent.isScheduled() && newEvent.isActive()) { console.log("Starting Event: " + newEvent.id); await new Promise((r) => setTimeout(r, 2000)); @@ -65,7 +71,7 @@ export const guildScheduledEventUpdate = new Event({ scheduledStart: newEvent.scheduledStartAt, name: newEvent.name, status: newEvent.status, - })) as IScheduledEvent; //maybe this should return null + })) as IScheduledEvent; // Maybe this should return null } else { res.recurrence = newEvent.recurrenceRule ? true : false; res.thumbnailUrl = @@ -80,6 +86,8 @@ export const guildScheduledEventUpdate = new Event({ } } + // If the current event is a recurring event that is active, and the updated event is scheduled. It will update the recurring event ending today and log it. + if (!res.recurrence) { if (oldEvent.isActive() && newEvent.isCompleted()) { console.log("ending one time event: " + newEvent.id); @@ -88,6 +96,7 @@ export const guildScheduledEventUpdate = new Event({ await logScheduledEvent(res); } } else { + // If the event is one-time and the Oldevent is marked active, and the new event is marked completed. It will update the one-time event ending today and log it. if (oldEvent.isActive() && newEvent.isScheduled()) { console.log("ending recurring event: " + newEvent.id); res.endedAt = new Date(Date.now()); diff --git a/src/features/logging/scheduledEvent.ts b/src/features/logging/scheduledEvent.ts index cfc0dd2..a286f2a 100644 --- a/src/features/logging/scheduledEvent.ts +++ b/src/features/logging/scheduledEvent.ts @@ -24,27 +24,32 @@ import dbConnect from "../../util/libmongo.js"; import { ScheduledEventWrapper } from "../../util/scheduledEventWrapper.js"; /** + * Records schelude event object in logs + * @param event Sheduled Event Object + * @param guild ?? + * @param forceNew ?? * - * @param event - * @param guild - * @param forceNew */ export async function logScheduledEvent(event: IScheduledEvent) { await dbConnect(); + // Gets guild object by guild ID from event object const guild: Guild = await client.guilds.fetch(event.guildId); + // Get settings by guild ID const settings = await GuildSetting.findOne({ guildId: guild.id }).exec(); const logChannelId = settings?.logging.eventLogChannelId; + // Checks if log channel ID exists if (!logChannelId) return; + // Finds channel from guid's channels cache by log Channel Id let logChannel = guild.channels.cache.get(logChannelId); if (!logChannel) { logChannel = (await guild.channels.fetch(logChannelId)) ?? undefined; } - + // Check if channel type is GuildText if (logChannel?.type !== ChannelType.GuildText) return; let existingPost = undefined; if (event.logMessageId) { - //console.log("finding existing post"); + // console.log("finding existing post"); existingPost = logChannel.messages.cache.get(event.logMessageId); if (!existingPost) { existingPost = await logChannel.messages @@ -61,12 +66,12 @@ export async function logScheduledEvent(event: IScheduledEvent) { } } - //console.log("fetched post"); + // console.log("fetched post"); //console.log(existingPost); if (existingPost) { - //console.log("editing existing post..."); - //console.log("event ended at: " + event.endedAt); + // console.log("editing existing post..."); + // console.log("event ended at: " + event.endedAt); const { cont } = await logContainer(event); const files = []; if (event.thumbnailUrl === "attachment://image.jpg") @@ -91,7 +96,7 @@ export async function logScheduledEvent(event: IScheduledEvent) { allowedMentions: { parse: [] }, }); event.logMessageId = post.id; - //console.log("event log message id: " + event.logMessageId); + // console.log("event log message id: " + event.logMessageId); await event.save(); } } @@ -102,12 +107,12 @@ export async function logScheduledEvent(event: IScheduledEvent) { */ async function logContainer(event: IScheduledEvent) { const wrapper = new ScheduledEventWrapper(event); - let attendees = wrapper.attendancePercentages(); + const attendees = wrapper.attendancePercentages(); const attendeesCount = wrapper.uniqueAttendees(); await wrapper.writeCsvDump(); - //if attendees.length > 30 then replace inline list with text file - //todo: figure out how to generate text file - //todo: add some file output for attachments in this function; wire it up to the main log function + // If attendees.length > 30 then replace inline list with text file + // TODO: figure out how to generate text file + // TODO: add some file output for attachments in this function; wire it up to the main log function const attendeesStr = attendees.length > 0 && attendees.length < 30 ? attendees diff --git a/src/models/ScheduledEvent.ts b/src/models/ScheduledEvent.ts index 0d6274c..da59dd2 100644 --- a/src/models/ScheduledEvent.ts +++ b/src/models/ScheduledEvent.ts @@ -1,6 +1,8 @@ import { GuildScheduledEventStatus, Snowflake } from "discord.js"; import mongoose, { Document, Model, Schema } from "mongoose"; - +/** + * {@link IScheduledEvent} + */ export interface IScheduledEvent extends Document { recurrence: boolean; eventUrl: string; diff --git a/src/util/.DS_Store b/src/util/.DS_Store new file mode 100644 index 0000000..40035c0 Binary files /dev/null and b/src/util/.DS_Store differ diff --git a/src/util/scheduledEventWrapper.ts b/src/util/scheduledEventWrapper.ts index b63443a..552440b 100644 --- a/src/util/scheduledEventWrapper.ts +++ b/src/util/scheduledEventWrapper.ts @@ -2,26 +2,30 @@ import createCsvWriter from "csv-writer"; import { GuildMember, GuildScheduledEventStatus, time } from "discord.js"; import { client } from "../index.js"; import { IScheduledEvent } from "../models/ScheduledEvent.js"; - +/** + * + * Wrapper class that returns a Schelude event for end user comsumption + * @returns{@link ScheduledEventWrapper} + */ export class ScheduledEventWrapper { event: IScheduledEvent; statusColor = () => { let color: number; switch (this.event.status) { - case 1: // scheduled = completed = blue + case 1: // Scheduled = completed = blue color = 0x3498db; break; - case 2: // active = green + case 2: // Active = green color = 0x57f386; break; - case 3: // completed = blue + case 3: // Completed = blue color = 0x3498db; break; - case 4: // cancelled = red + case 4: // Cancelled = red color = 0xed4245; break; - default: // undefined = white + default: // Undefined = white color = 0xffffff; } @@ -223,7 +227,7 @@ export class ScheduledEventWrapper { private async getAttendeeNames(ids: string[]) { const buffer = []; - let names: Map = new Map(); + const names: Map = new Map(); for (let i = 0; i < Math.ceil(ids.length / 100); i++) { const slice = ids.slice( i * 100,