// This file is part of Macy . // Copyright (C) 2022-2022 Fuwn // // All Rights Reserved. // // Copyright (C) 2022-2022 Fuwn // SPDX-License-Identifier: UNLICENSED import { APPROVED_ROLE, CLASS_MEMBERS, FUWN_ID, LOBBY_CHANNEL, } from "./config.ts"; import { ApplicationCommandInteraction, ApplicationCommandOptionType, Client, event, PermissionFlags, slash, } from "https://deno.land/x/harmony@v2.6.0/mod.ts"; export class Macy extends Client { verificationQueue = new Map(); @event() ready() { console.log(`${this.user?.username}#${this.user?.discriminator} is ready!`); this.user?.client.setPresence({ activity: { name: "your work", type: "WATCHING", }, }); this.interactions.commands.bulkEdit([ { name: "setup", description: "Setup the informational message in the lobby channel", }, { name: "queue", description: "View the verification queue", }, { name: "verify", description: "Add your account to the verification queue", options: [ { name: "name", description: "Your full name as shown in Zoom", required: true, type: ApplicationCommandOptionType.STRING, }, ], }, { name: "approve", description: "Approve an account in the verification queue", options: [ { name: "name", description: "A users full name as shown in Zoom. If not specified, all " + "queued accounts will be approved.", required: false, type: ApplicationCommandOptionType.STRING, }, ], }, { name: "check", description: "Check if you are recognized as a class member", options: [ { name: "name", description: "Your full name as shown in Zoom", required: true, type: ApplicationCommandOptionType.STRING, }, ], }, ]); console.log("Commands setup!"); } @slash() setup(_: ApplicationCommandInteraction) { this.user?.client?.channels.sendMessage( LOBBY_CHANNEL, "To access the rest of the server, send a message structured like this: " + "`/verify [name]`, with `name` being your full name as shown in Zoom." + "\n\nAn example of a valid verification request looks like this: " + "`/verify Zoltan Szabatin`.\n\nIf you are unable to verify yourself; " + "first, check if your name is recognized as a class member using the " + "`/check [name]` command, with `name` being your full name as show in " + "Zoom. An example of a valid check command looks like: " + "`/check Zoltan Szabatin`.\n\nIf you are unable to verify yourself and " + "your name is not recognized as a class member, you should then DM " + `<@${FUWN_ID}>.`, ); } @slash() async verify(d: ApplicationCommandInteraction) { const member = d.member; const name = d.option("name"); if (member === null) { d.respond({ content: "I cannot obtain your ID, please try again.", ephemeral: true, }); return; } if ((await member?.roles.get(APPROVED_ROLE)) !== undefined) { d.respond({ content: "You are already verified!", ephemeral: true, }); return; } this.verificationQueue.forEach((verificationName, id) => { if (id === member?.id || verificationName === name) { d.respond({ content: "You are already in the verification queue!", ephemeral: true, }); return; } }); if ( Deno.env.get("CLASS")?.toLowerCase() === "true" || Deno.env.get("CLASS") === "1" ) { if (!CLASS_MEMBERS.includes(name)) { d.respond({ content: "You are not a class member!", ephemeral: true, }); return; } } (await d.guild?.members.fetchList())?.forEach((member) => { if (member.nick === name) { d.respond({ content: "Someone with that exact name is already verified! If you " + `think this is an error, DM <@${FUWN_ID}>.`, ephemeral: true, }); return; } }); this.verificationQueue.set(name, member!.id); d.respond({ content: `Hello, ${name}! You have been added into the verification queue and ` + "will be verified shortly.", ephemeral: true, }); } @slash() async approve(d: ApplicationCommandInteraction) { if (this.verificationQueue.size === 0) { d.reply("There are no users in the verification queue."); return; } const name = d.option("name"); if ( !(d.member?.permissions.has(PermissionFlags.ADMINISTRATOR)) ) { d.respond({ content: "You do not have sufficient permissions to verify this user!", ephemeral: true, }); return; } if (name === undefined) { console.log(this.verificationQueue); this.verificationQueue.forEach(async (id, name) => { this.verificationQueue.delete(name); (await d.guild!.members.get(id))?.roles.add(APPROVED_ROLE); (await d.guild!.members.get(id))?.setNickname(name); }); d.reply("All users within the verification queue have been approved!"); } else { const member = this.verificationQueue.get(name); if (member === undefined) { d.reply(`${name} is not in the verification queue.`); } else { this.verificationQueue.delete(name); (await d.guild!.members.get(member))?.roles.add(APPROVED_ROLE); (await d.guild!.members.get(member))?.setNickname(name); d.reply(`${name} has been approved!`); } } } @slash() queue(d: ApplicationCommandInteraction) { if (this.verificationQueue.size === 0) { d.reply("There are no users in the verification queue."); return; } let verificationQueueString = "Map { "; let i = 1; this.verificationQueue.forEach((name, id) => { verificationQueueString += `\"${id}\" => \"${name}\" ${ i == this.verificationQueue.size ? "" : ", " }`; i += 1; }); d.reply(verificationQueueString + "}"); } @slash() check(d: ApplicationCommandInteraction) { const name = d.option("name"); if (CLASS_MEMBERS.includes(name)) { d.reply(`${name} is a class member!`); } else { d.reply(`${name} is not a class member!`); } } }