HiddenPhox/src/modules/utility.js

579 lines
15 KiB
JavaScript
Raw Normal View History

2021-06-02 00:31:39 +00:00
const Command = require("../lib/command.js");
2021-06-02 00:32:30 +00:00
const CATEGORY = "utility";
2021-06-02 00:31:39 +00:00
const ICON_BASE = "https://cdn.discordapp.com/icons/";
const AVATAR_BASE = "https://cdn.discordapp.com/avatars/";
2021-06-02 00:58:39 +00:00
const SPLASH_BASE = "https://cdn.discordapp.com/splashes/";
const BANNER_BASE = "https://cdn.discordapp.com/banners/";
2021-08-12 03:31:56 +00:00
const EMOTE_BASE = "https://cdn.discordapp.com/emojis/";
2021-06-02 00:58:39 +00:00
const STATUS_ICONS = {
online: "<:online:493173082421461002>",
idle: "<:idle:493173082006093836>",
dnd: "<:dnd:493173082261815307>",
offline: "<:offline:493173082253426688>",
};
2021-06-02 00:31:39 +00:00
2021-08-12 03:31:56 +00:00
const EMOJI_SETS = {
blobs: {
prefix:
"https://cdn.jsdelivr.net/gh/googlefonts/noto-emoji@e456654119cc3a5f9bebb7bbd00512456f983d2d/svg/emoji_u",
sep: "_",
suffix: ".svg",
},
noto: {
prefix: "gitcdn.xyz/repo/googlefonts/noto-emoji/master/svg/emoji_u",
sep: "_",
suffix: ".svg",
},
twemoji: {
prefix: "https://twemoji.maxcdn.com/v/latest/svg/",
sep: "-",
suffix: ".svg",
},
mustd: {
prefix:
"https://cdn.jsdelivr.net/gh/Mstrodl/mutant-standard-mirror@0435227d9d8c0d6a346c8ae4c12b08a5cdc37041/emoji/",
sep: "-",
suffix: ".svg",
},
apple: {
prefix: "https://intrnl.github.io/assetsEmoji/AppleColor/emoji_u",
sep: "_",
suffix: ".png",
},
facebook: {
prefix: "https://intrnl.github.io/assetsEmoji/facebook/emoji_u",
sep: "_",
suffix: ".png",
},
};
EMOJI_SETS["noto-old"] = EMOJI_SETS.blobs;
EMOJI_SETS.mutant = EMOJI_SETS.mustd;
EMOJI_SETS.mutstd = EMOJI_SETS.mustd;
EMOJI_SETS.ms = EMOJI_SETS.mustd;
EMOJI_SETS.twitter = EMOJI_SETS.twemoji;
EMOJI_SETS.fb = EMOJI_SETS.facebook;
2021-08-12 03:33:58 +00:00
const CUSTOM_EMOTE_REGEX = /<(?:\u200b|&)?(a)?:(\w+):(\d+)>/;
2021-08-12 03:31:56 +00:00
const fetch = require("node-fetch");
const sharp = require("sharp");
2021-08-12 02:41:28 +00:00
const {lookupUser} = require("../lib/utils.js");
2021-08-12 03:31:56 +00:00
const {getNamesFromString} = require("../lib/unicode.js");
2021-06-02 00:31:39 +00:00
const avatar = new Command("avatar");
avatar.category = CATEGORY;
avatar.helpText = "Get avatar of a user";
avatar.usage = "<user>";
avatar.callback = async function (msg, line) {
if (line == "--server" || line == "--guild") {
if (!msg.guildID) {
2021-06-02 00:31:39 +00:00
return "`--server/--guild` can only be used within guilds.";
} else {
const guild = msg.channel.guild || hf.bot.guilds.get(msg.guildID);
const url = `${ICON_BASE}${guild.id}/${guild.icon}.${
guild.icon.startsWith("a_") ? "gif?size=1024&_=.gif" : "png?size=1024"
2021-06-02 00:31:39 +00:00
}`;
return {
embeds: [
{
title: "Server Icon",
2021-06-02 00:31:39 +00:00
url,
image: {
url,
},
2021-06-02 00:31:39 +00:00
},
],
2021-06-02 00:31:39 +00:00
};
}
} else if (line) {
const user = await lookupUser(msg, line);
if (
user == "No results" ||
user == "Canceled" ||
user == "Request timed out"
) {
return user;
} else {
let member = user;
const guild = msg.channel.guild || hf.bot.guilds.get(msg.guildID);
if (guild) {
if (guild.members.has(user.id)) {
member = guild.members.get(user.id);
} else {
const fetched = await guild.fetchMembers({
userIDs: [user.id],
});
member = fetched[0];
}
}
const avatar = member.avatar || member.user.avatar;
const url =
guild && member.avatar
? `https://cdn.discordapp.com/guilds/${guild.id}/users/${
member.id
}/avatars/${member.avatar}.${
member.avatar.startsWith("a_")
? "gif?size=1024&_=.gif"
: "png?size=1024"
}`
: `${AVATAR_BASE}${member.id}/${avatar}.${
avatar.startsWith("a_") ? "gif?size=1024&_=.gif" : "png?size=1024"
}`;
2021-06-02 00:31:39 +00:00
return {
embeds: [
{
title: `Avatar for \`${member.username}#${member.discriminator}\``,
2021-06-02 00:31:39 +00:00
url,
image: {
url,
},
2021-06-02 00:31:39 +00:00
},
],
2021-06-02 00:31:39 +00:00
};
}
} else {
const guild = msg.channel.guild || hf.bot.guilds.get(msg.guildID);
const avatar = msg.member.avatar || msg.author.avatar;
const url = msg.member.avatar
? `https://cdn.discordapp.com/guilds/${guild.id}/users/${
msg.member.id
}/avatars/${msg.member.avatar}.${
msg.member.avatar.startsWith("a_")
? "gif?size=1024&_=.gif"
: "png?size=1024"
}`
: `${AVATAR_BASE}${msg.author.id}/${avatar}.${
avatar.startsWith("a_") ? "gif?size=1024&_=.gif" : "png?size=1024"
}`;
2021-06-02 00:31:39 +00:00
return {
embeds: [
{
title: `Avatar for \`${msg.author.username}#${msg.author.discriminator}\``,
2021-06-02 00:31:39 +00:00
url,
image: {
url,
},
2021-06-02 00:31:39 +00:00
},
],
2021-06-02 00:31:39 +00:00
};
}
};
hf.registerCommand(avatar);
2021-06-02 00:58:39 +00:00
2021-07-28 17:56:27 +00:00
const banner = new Command("banner");
banner.category = CATEGORY;
banner.helpText = "Get banner of a user";
banner.usage = "<user>";
banner.callback = async function (msg, line) {
let id = msg.author.id;
2021-08-26 17:18:50 +00:00
if (line == "--server" || line == "--guild") {
if (!msg.guildID) {
2021-08-26 17:18:50 +00:00
return "`--server/--guild` can only be used within guilds.";
} else {
const guild = msg.channel.guild || hf.bot.guilds.get(msg.guildID);
2021-08-31 15:49:21 +00:00
if (!guild.banner) return "This guild does not have a banner.";
const url = `${BANNER_BASE}${guild.id}/${guild.banner}.${
guild.banner.startsWith("a_") ? "gif?size=1024&_=.gif" : "png?size=1024"
2021-08-26 17:18:50 +00:00
}`;
return {
embeds: [
{
title: "Server Banner",
2021-08-26 17:18:50 +00:00
url,
image: {
url,
},
2021-08-26 17:18:50 +00:00
},
],
2021-08-26 17:18:50 +00:00
};
}
} else if (line) {
2021-07-28 17:56:27 +00:00
const lookup = await lookupUser(msg, line);
if (
lookup == "No results" ||
lookup == "Canceled" ||
lookup == "Request timed out"
) {
return lookup;
} else {
id = lookup.id;
}
}
const user = await hf.bot.requestHandler.request("GET", "/users/" + id, true);
if (!user.banner) return "This user does not have a banner.";
const url = `${BANNER_BASE}${user.id}/${user.banner}.${
user.banner.startsWith("a_") ? "gif?size=1024&_=.gif" : "png?size=1024"
}`;
return {
embeds: [
{
title: `Banner for \`${user.username}#${user.discriminator}\``,
2021-07-28 17:56:27 +00:00
url,
image: {
url,
},
2021-07-28 17:56:27 +00:00
},
],
2021-07-28 17:56:27 +00:00
};
};
hf.registerCommand(banner);
2021-06-02 00:58:39 +00:00
const lookupinvite = new Command("lookupinvite");
lookupinvite.category = CATEGORY;
lookupinvite.helpText = "Lookup an invite";
lookupinvite.usage = "<invite code>";
lookupinvite.addAlias("linvite");
lookupinvite.callback = async function (msg, line) {
if (!line) {
return "No arguments passed.";
}
line = line.replace(/(https?:\/\/)?discord\.gg\//, "");
const invite = await hf.bot.requestHandler.request(
"GET",
"/invites/" + line + "?with_counts=1"
);
if (!invite) return ":warning: No data returned.";
if (invite.message) {
if (invite.message == "Unknown Invite") {
return "Invite provided is not valid.";
} else {
return `:warning: Got error \`${invite.code}: "${invite.message}"\``;
}
} else {
const embed = {
title: `Invite Info: \`${invite.code}\``,
description: invite.description,
fields: [
{
name: "Guild",
value: `**${invite.guild.name}** (${invite.guild.id})`,
inline: true,
},
{
name: "Channel",
value: `**${invite.channel.name}** (${invite.channel.id})`,
inline: true,
},
{
name: "Member Count",
value: `${STATUS_ICONS.online}${invite.approximate_presence_count} online\t\t${STATUS_ICONS.offline}${invite.approximate_member_count} members`,
inline: false,
},
{
name: "Features",
value:
invite.guild.features.length > 0
? invite.guild.features
.map((feature) =>
feature
.split("_")
.map((x) => x[0] + x.substring(1).toLowerCase())
.join(" ")
)
.join(", ")
: "None",
inline: false,
},
],
thumbnail: {
url:
invite.guild.icon &&
`${ICON_BASE}${invite.guild.id}/${invite.guild.icon}.${
invite.guild.icon.startsWith("a_")
? "gif?size=1024&_=.gif"
: "png?size=1024"
}`,
},
};
if (invite.inviter) {
embed.fields.push({
name: "Inviter",
value: `**${invite.inviter.username}#${invite.inviter.discriminator}** (${invite.inviter.id})`,
inline: true,
});
}
if (invite.guild.icon || invite.guild.splash || invite.guild.banner) {
embed.fields.push({
name: "\u200b",
value: `${
invite.guild.icon
? `[Icon](${ICON_BASE}${invite.guild.id}/${invite.guild.icon}.${
invite.guild.icon.startsWith("a_")
? "gif?size=1024"
: "png?size=1024"
})`
: ""
}${
invite.guild.splash
? `${invite.guild.icon ? " | " : ""}[Splash](${SPLASH_BASE}${
invite.guild.id
}/${invite.guild.splash}.png?size=2048)`
: ""
}${
invite.guild.banner
? `${
invite.guild.icon || invite.guild.splash ? " | " : ""
}[Banner](${BANNER_BASE}${invite.guild.id}/${
invite.guild.banner
}.png?size=2048)`
: ""
}`,
inline: false,
});
}
if (invite.guild.splash) {
embed.image = {
url: `${SPLASH_BASE}${invite.guild.id}/${invite.guild.splash}.png?size=256`,
};
}
return {embed};
}
};
hf.registerCommand(lookupinvite);
2021-06-11 03:54:17 +00:00
const snowflake = new Command("snowflake");
snowflake.category = CATEGORY;
snowflake.helpText = "Converts a snowflake ID into readable time.";
snowflake.usage = "<--twitter> [snowflake]";
snowflake.callback = function (msg, line) {
let twitter = false;
if (line.startsWith("--twitter")) {
twitter = true;
line.replace("--twitter ", "");
}
const num = parseInt(line);
if (!isNaN(num)) {
let binary = num.toString(2);
binary = "0".repeat(64 - binary.length) + binary;
const timestamp =
parseInt(binary.substr(0, 42), 2) +
(twitter ? 1288834974657 : 1420070400000);
2021-08-04 23:15:21 +00:00
return `The timestamp for \`${line}\` is ${new Date(
timestamp
).toUTCString()}`;
2021-06-11 03:54:17 +00:00
} else {
return "Argument provided is not a number.";
}
};
hf.registerCommand(snowflake);
const USER_FLAGS = [
"STAFF",
"PARTNER",
"HYPESQUAD",
"BUG_HUNTER_LEVEL_1",
"MFA_SMS",
"PREMIUM_PROMO_DISMISSED",
"HYPESQUAD_ONLINE_HOUSE_1",
"HYPESQUAD_ONLINE_HOUSE_2",
"HYPESQUAD_ONLINE_HOUSE_3",
"PREMIUM_EARLY_SUPPORTER",
"TEAM_PSEUDO_USER",
"<Internal Application (Partner, etc) Flag>",
"SYSTEM",
"HAS_UNREAD_URGENT_MESSAGES",
"BUG_HUNTER_LEVEL_2",
"UNDERAGE_DELETED",
"VERIFIED_BOT",
"VERIFIED_DEVELOPER",
"CERTIFIED_MODERATOR",
"BOT_HTTP_INTERACTIONS",
2021-10-16 03:09:55 +00:00
"SPAMMER",
2021-08-04 23:15:21 +00:00
undefined,
undefined,
undefined,
undefined,
undefined,
undefined,
undefined,
undefined,
undefined,
undefined,
undefined,
undefined,
undefined,
undefined,
undefined,
undefined,
undefined,
undefined,
undefined,
undefined,
undefined,
undefined,
"<Verified Phone Number (speculative)>",
];
2021-06-22 04:35:04 +00:00
function flagFromInt(int) {
const bits = int.toString(2);
const splitBits = bits.split("").reverse();
2021-06-22 04:35:04 +00:00
const reassignedBits = {};
2021-06-22 04:35:04 +00:00
for (const shift in splitBits) {
reassignedBits[shift] = splitBits[shift];
}
2021-06-22 04:35:04 +00:00
const flags = Object.keys(reassignedBits).filter(
(bit) => reassignedBits[bit] == 1
);
2021-06-22 04:35:04 +00:00
let out = "";
for (const flag of flags) {
out +=
(USER_FLAGS[flag] || "<Undocumented Flag>") +
` (1 << ${flag}, ${1n << BigInt(flag)})\n`;
}
2021-06-22 04:35:04 +00:00
return out;
}
const flagdump = new Command("flagdump");
flagdump.category = CATEGORY;
flagdump.helpText = "Dumps Discord user flags.";
flagdump.usage = "[flags or user mention]";
flagdump.callback = async function (msg, line) {
const num = parseInt(line);
if (/<@!?([0-9]*)>/.test(line)) {
const id = line.match(/<@?!([0-9]*)>/)[1];
const guild = msg.channel.guild || hf.bot.guilds.get(msg.guildID);
let user = guild && (await guild.fetchMembers({userIDs: [id]}));
if (!user || !user[0]) {
2021-06-22 04:35:04 +00:00
user = hf.bot.users.get(id);
} else {
user = user[0].user;
}
2021-06-22 04:35:04 +00:00
if (!user) {
return "User not cached.";
} else {
return `\`${user.username}#${
user.discriminator
}\`'s public flags:\n\`\`\`${flagFromInt(user.publicFlags)}\`\`\``;
}
} else if (!isNaN(num)) {
return `\`\`\`\n${flagFromInt(num)}\`\`\``;
} else {
2021-06-22 04:35:04 +00:00
return `\`${msg.author.username}#${
msg.author.discriminator
}\`'s public flags:\n\`\`\`${flagFromInt(msg.author.publicFlags)}\`\`\``;
}
};
hf.registerCommand(flagdump);
2021-08-12 03:31:56 +00:00
const emojiNames = [];
fetch("https://unpkg.com/emoji.json/emoji.json")
.then((res) => res.json())
.then((body) =>
body.map(
(emoji) => (emojiNames[emoji.char] = emoji.name.replace(/ /g, "_"))
)
);
const jumbo = new Command("jumbo");
jumbo.category = CATEGORY;
jumbo.helpText = "Gets the raw image of an emoji.";
jumbo.usage = "<emoji>";
jumbo.addAlias("e");
jumbo.addAlias("emote");
jumbo.addAlias("emoji");
jumbo.callback = async function (msg, line) {
if (CUSTOM_EMOTE_REGEX.test(line)) {
2021-08-12 03:33:58 +00:00
const [_, animatedFlag, name, id] = line.match(CUSTOM_EMOTE_REGEX);
2021-08-12 03:31:56 +00:00
const animated = animatedFlag === "a";
return {
embeds: [
{
title: `:${name}: - \`${id}\``,
2021-08-12 03:31:56 +00:00
url: `${EMOTE_BASE}${id}.${animated ? "gif" : "png"}?v=1`,
image: {
url: `${EMOTE_BASE}${id}.${animated ? "gif" : "png"}?v=1`,
},
2021-08-12 03:31:56 +00:00
},
],
2021-08-12 03:31:56 +00:00
};
} else {
let setName = "twemoji";
for (const set in EMOJI_SETS) {
if (line.startsWith(`--${set} `)) {
setName = set;
line = line.replace(`--${set} `, "");
}
}
const set = EMOJI_SETS[setName];
const emoji = Array.from(line)
.map((char) => char.codePointAt().toString(16))
.join(set.sep);
const url = set.prefix + emoji + set.suffix;
const name = emojiNames[line]
? `\\:${emojiNames[line]}\\:`
: getNamesFromString(line)[0][1];
const statusCode = await fetch(url, {method: "HEAD"}).then(
(res) => res.status
);
if (statusCode !== 200) {
return "Emoji not found. The emoji set chosen might not have this emote as an image.";
}
if (set.suffix == ".svg") {
const svg = await fetch(url).then((res) => res.buffer());
const converted = await sharp(svg, {density: 2400})
.resize(1024)
.toBuffer();
return {
embeds: [
{
title: `${name} (${emoji.toUpperCase().replace(/[-_]/g, ", ")})`,
url,
image: {
url: "attachment://emoji.png",
},
2021-08-12 03:31:56 +00:00
},
],
2021-08-12 03:31:56 +00:00
file: {
file: converted,
name: "emoji.png",
},
};
} else {
return {
embeds: [
{
title: `${name} (${emoji.toUpperCase().replace(/[-_]/g, ", ")})`,
2021-08-12 03:31:56 +00:00
url,
image: {
url,
},
2021-08-12 03:31:56 +00:00
},
],
2021-08-12 03:31:56 +00:00
};
}
}
};
hf.registerCommand(jumbo);