Fix everything

Matt please don't change the ECMA target
merge-requests/9/merge
Bsian 2020-04-17 03:56:52 +01:00
parent 4069a20a31
commit cfe5e65ed8
No known key found for this signature in database
GPG Key ID: 097FB9A291026091
14 changed files with 107 additions and 93 deletions

View File

@ -22,7 +22,7 @@
}, },
"dependencies": { "dependencies": {
"axios": "^0.19.2", "axios": "^0.19.2",
"eris": "^0.11.2", "eris": "abalabahaha/eris#dev",
"moment": "^2.24.0", "moment": "^2.24.0",
"mongoose": "^5.9.9", "mongoose": "^5.9.9",
"signale": "^1.4.0", "signale": "^1.4.0",

View File

@ -2,12 +2,12 @@
* Hold a bunch of something * Hold a bunch of something
*/ */
export default class Collection<V> extends Map<string, V> { export default class Collection<V> extends Map<string, V> {
baseObject: any baseObject: new (...args: any[]) => V;
/** /**
* Creates an instance of Collection * Creates an instance of Collection
*/ */
constructor(iterable: any[]|object = null) { constructor(iterable: Iterable<[string, V]>|object = null) {
if (iterable && iterable instanceof Array) { if (iterable && iterable instanceof Array) {
super(iterable); super(iterable);
} else if (iterable && iterable instanceof Object) { } else if (iterable && iterable instanceof Object) {
@ -33,8 +33,8 @@ export default class Collection<V> extends Map<string, V> {
* { key: value, key: value, key: value } * { key: value, key: value, key: value }
* ``` * ```
*/ */
toObject(): object { toObject(): { [key: string]: V } {
const obj: object = {}; const obj: { [key: string]: V } = {};
for (const [key, value] of this.entries()) { for (const [key, value] of this.entries()) {
obj[key] = value; obj[key] = value;
} }
@ -90,7 +90,7 @@ export default class Collection<V> extends Map<string, V> {
* Return all the objects that make the function evaluate true * Return all the objects that make the function evaluate true
* @param func A function that takes an object and returns true if it matches * @param func A function that takes an object and returns true if it matches
*/ */
filter(func: Function): V[] { filter(func: (value: V) => boolean): V[] {
const arr = []; const arr = [];
for (const item of this.values()) { for (const item of this.values()) {
if (func(item)) { if (func(item)) {
@ -104,7 +104,7 @@ export default class Collection<V> extends Map<string, V> {
* Test if at least one element passes the test implemented by the provided function. Returns true if yes, or false if not. * Test if at least one element passes the test implemented by the provided function. Returns true if yes, or false if not.
* @param func A function that takes an object and returns true if it matches * @param func A function that takes an object and returns true if it matches
*/ */
some(func: Function) { some(func: (value: V) => boolean) {
for (const item of this.values()) { for (const item of this.values()) {
if (func(item)) { if (func(item)) {
return true; return true;

View File

@ -1,4 +1,4 @@
import { Member, Message } from 'eris'; import { Member, Message, TextableChannel } from 'eris';
import { Client } from '.'; import { Client } from '.';
export default class Command { export default class Command {
@ -68,4 +68,16 @@ export default class Command {
return false; return false;
} }
} }
public error(channel: TextableChannel, text: string): Promise<Message> {
return channel.createMessage(`***${this.client.util.emojis.ERROR} ${text}***`);
}
public success(channel: TextableChannel, text: string): Promise<Message> {
return channel.createMessage(`***${this.client.util.emojis.SUCCESS} ${text}***`);
}
public loading(channel: TextableChannel, text: string): Promise<Message> {
return channel.createMessage(`***${this.client.util.emojis.LOADING} ${text}***`);
}
} }

View File

@ -41,13 +41,14 @@ export default class Moderation {
} }
public async ban(user: User, moderator: Member, duration: number, reason?: string): Promise<ModerationInterface> { public async ban(user: User, moderator: Member, duration: number, reason?: string): Promise<ModerationInterface> {
if (reason && reason.length > 512) throw new Error('Ban reason cannot be longer than 512 characters');
await this.client.guilds.get(this.client.config.guildID).banMember(user.id, 7, reason); await this.client.guilds.get(this.client.config.guildID).banMember(user.id, 7, reason);
const logID = uuid(); const logID = uuid();
const mod = new ModerationModel({ const mod = new ModerationModel({
userID: user.id, userID: user.id,
logID, logID,
moderatorID: moderator.id, moderatorID: moderator.id,
reason: reason ?? null, reason: reason || null,
type: 5, type: 5,
date: new Date(), date: new Date(),
}); });
@ -89,7 +90,7 @@ export default class Moderation {
userID, userID,
logID, logID,
moderatorID: moderator.id, moderatorID: moderator.id,
reason: reason ?? null, reason: reason || null,
type: 4, type: 4,
date: new Date(), date: new Date(),
}); });

View File

@ -1,6 +1,20 @@
/* eslint-disable no-param-reassign */ /* eslint-disable no-param-reassign */
export default class RichEmbed { export interface EmbedData {
title?: string
description?: string
url?: string
timestamp?: Date
color?: number
footer?: { text: string, icon_url?: string, proxy_icon_url?: string}
image?: { url: string, proxy_url?: string, height?: number, width?: number }
thumbnail?: { url: string, proxy_url?: string, height?: number, width?: number }
video?: { url: string, height?: number, width?: number }
author?: { name: string, url?: string, proxy_icon_url?: string, icon_url?: string}
fields?: {name: string, value: string, inline?: boolean}[]
}
export default class RichEmbed implements EmbedData {
title?: string title?: string
type?: string type?: string
@ -17,7 +31,7 @@ export default class RichEmbed {
image?: { url: string, proxy_url?: string, height?: number, width?: number } image?: { url: string, proxy_url?: string, height?: number, width?: number }
thumbnail?: { url?: string, proxy_url?: string, height?: number, width?: number } thumbnail?: { url: string, proxy_url?: string, height?: number, width?: number }
video?: { url: string, height?: number, width?: number } video?: { url: string, height?: number, width?: number }
@ -27,12 +41,7 @@ export default class RichEmbed {
fields?: {name: string, value: string, inline?: boolean}[] fields?: {name: string, value: string, inline?: boolean}[]
constructor(data: { constructor(data: EmbedData = {}) {
title?: string, type?: string, description?: string, url?: string, timestamp?: Date, color?: number, fields?: {name: string, value: string, inline?: boolean}[]
footer?: { text: string, icon_url?: string, proxy_icon_url?: string}, image?: { url: string, proxy_url?: string, height?: number, width?: number },
thumbnail?: { url: string, proxy_url?: string, height?: number, width?: number }, video?: { url: string, height?: number, width?: number },
provider?: { name: string, url?: string}, author?: { name: string, url?: string, proxy_icon_url?: string, icon_url?: string},
} = {}) {
/* /*
let types: { let types: {
title?: string, type?: string, description?: string, url?: string, timestamp?: Date, color?: number, fields?: {name: string, value: string, inline?: boolean}[] title?: string, type?: string, description?: string, url?: string, timestamp?: Date, color?: number, fields?: {name: string, value: string, inline?: boolean}[]
@ -79,7 +88,7 @@ export default class RichEmbed {
setURL(url: string) { setURL(url: string) {
if (typeof url !== 'string') throw new TypeError('RichEmbed URLs must be a string.'); if (typeof url !== 'string') throw new TypeError('RichEmbed URLs must be a string.');
if (!url.startsWith('http://') || !url.startsWith('https://')) url = `https://${url}`; if (!url.startsWith('http://') || !url.startsWith('https://')) url = `https://${url}`;
this.url = url; this.url = encodeURI(url);
return this; return this;
} }

View File

@ -1,3 +1,4 @@
/* eslint-disable no-bitwise */
import signale from 'signale'; import signale from 'signale';
import { Member, Message, Guild, PrivateChannel, GroupChannel, Role, AnyGuildChannel } from 'eris'; import { Member, Message, Guild, PrivateChannel, GroupChannel, Role, AnyGuildChannel } from 'eris';
import { Client, Command, Moderation, RichEmbed } from '.'; import { Client, Command, Moderation, RichEmbed } from '.';
@ -50,17 +51,21 @@ export default class Util {
} }
} }
public resolveGuildChannel(query: string, { channels }: Guild): AnyGuildChannel | undefined { public resolveGuildChannel(query: string, { channels }: Guild, categories = false): AnyGuildChannel | undefined {
const nchannels = channels.map((c) => c).sort((a: AnyGuildChannel, b: AnyGuildChannel) => a.type - b.type); const ch: AnyGuildChannel[] = channels.filter((c) => (!categories ? c.type !== 4 : true));
return nchannels.find((c) => (c.id === query || c.name === query || c.name.toLowerCase() === query.toLowerCase() || c.name.toLowerCase().startsWith(query.toLowerCase()))); return ch.find((c) => c.id === query.replace(/[<#>]/g, '') || c.name === query)
|| ch.find((c) => c.name.toLowerCase() === query.toLowerCase())
|| ch.find((c) => c.name.toLowerCase().startsWith(query.toLowerCase()));
} }
public resolveRole(query: string, { roles }: Guild): Role | undefined { public resolveRole(query: string, { roles }: Guild): Role | undefined {
return roles.find((r) => r.id === query || r.name === query || r.name.toLowerCase() === query.toLowerCase() || r.name.toLowerCase().startsWith(query.toLowerCase())); return roles.find((r) => r.id === query.replace(/[<@&>]/g, '') || r.name === query)
|| roles.find((r) => r.name.toLowerCase() === query.toLowerCase())
|| roles.find((r) => r.name.toLowerCase().startsWith(query.toLowerCase()));
} }
public resolveMember(query: string, { members }: Guild): Member | undefined { public resolveMember(query: string, { members }: Guild): Member | undefined {
return members.find((m) => m.mention.replace('!', '') === query.replace('!', '') || `${m.username}#${m.discriminator}` === query || m.username === query || m.id === query || m.nick === query) // Exact match for mention, username+discrim, username and user ID return members.find((m) => `${m.username}#${m.discriminator}` === query || m.username === query || m.id === query.replace(/[<@!>]/g, '') || m.nick === query) // Exact match for mention, username+discrim, username and user ID
|| members.find((m) => `${m.username.toLowerCase()}#${m.discriminator}` === query.toLowerCase() || m.username.toLowerCase() === query.toLowerCase() || (m.nick && m.nick.toLowerCase() === query.toLowerCase())) // Case insensitive match for username+discrim, username || members.find((m) => `${m.username.toLowerCase()}#${m.discriminator}` === query.toLowerCase() || m.username.toLowerCase() === query.toLowerCase() || (m.nick && m.nick.toLowerCase() === query.toLowerCase())) // Case insensitive match for username+discrim, username
|| members.find((m) => m.username.toLowerCase().startsWith(query.toLowerCase()) || (m.nick && m.nick.toLowerCase().startsWith(query.toLowerCase()))); || members.find((m) => m.username.toLowerCase().startsWith(query.toLowerCase()) || (m.nick && m.nick.toLowerCase().startsWith(query.toLowerCase())));
} }
@ -85,10 +90,10 @@ export default class Util {
info.embed = embed; info.embed = embed;
} }
await this.client.createMessage('595788220764127272', info); await this.client.createMessage('595788220764127272', info);
const msg = message.content.slice(this.client.config.prefix.length).trim().split(/ +/g); const msg = message ? message.content.slice(this.client.config.prefix.length).trim().split(/ +/g) : [];
// eslint-disable-next-line no-param-reassign // eslint-disable-next-line no-param-reassign
if (command && disable) this.resolveCommand(msg).then((c) => { c.cmd.enabled = false; }); if (command && disable) this.resolveCommand(msg).then((c) => { c.cmd.enabled = false; });
if (message) message.channel.createMessage(`***${this.emojis.ERROR} An unexpected error has occured - please contact a Faculty Marshal.${command ? ' This command has been disabled.' : ''}***`); if (message) message.channel.createMessage(`***${this.emojis.ERROR} An unexpected error has occured - please contact a Faculty Marshal.${command && disable ? ' This command has been disabled.' : ''}***`);
} catch (err) { } catch (err) {
this.signale.error(err); this.signale.error(err);
} }
@ -112,4 +117,13 @@ export default class Util {
} }
return arrayString; return arrayString;
} }
public decimalToHex(int: number): string {
const red = (int && 0x0000ff) << 16;
const green = int && 0x00ff00;
const blue = (int && 0xff0000) >>> 16;
const number = red | green | blue;
const asHex = number.toString(16);
return '#000000'.substring(0, 7 - asHex.length) + asHex;
}
} }

View File

@ -1,5 +1,5 @@
import moment, { unitOfTime } from 'moment'; import moment, { unitOfTime } from 'moment';
import { Message, User } from 'eris'; import { Message, User, PrivateChannel, GroupChannel } from 'eris';
import { Client, Command } from '../class'; import { Client, Command } from '../class';
export default class Ban extends Command { export default class Ban extends Command {
@ -15,24 +15,20 @@ export default class Ban extends Command {
public async run(message: Message, args: string[]) { public async run(message: Message, args: string[]) {
try { try {
// @ts-ignore const member = this.client.util.resolveMember(args[0], message.member.guild);
const member = this.client.util.resolveMember(args[0], message.channel.guild);
let user: User; let user: User;
if (!member) { if (!member) {
try { try {
user = await this.client.getRESTUser(args[0]); user = await this.client.getRESTUser(args[0]);
} catch { } catch {
return message.channel.createMessage(`***${this.client.util.emojis.ERROR} Cannot find user.***`); return this.error(message.channel, 'Cannot find user.');
} }
} }
try { try {
await this.client.guilds.get(this.client.config.guildID).getBan(args[0]); await this.client.guilds.get(this.client.config.guildID).getBan(args[0]);
return message.channel.createMessage(`***${this.client.util.emojis.ERROR} This user is already banned.***`); return this.error(message.channel, 'This user is already banned.');
} catch { } catch {} // eslint-disable-line no-empty
// eslint-disable-next-line no-unused-expressions if (member && !this.client.util.moderation.checkPermissions(member, message.member)) return this.error(message.channel, 'Permission Denied.');
undefined;
}
if (member && !this.client.util.moderation.checkPermissions(member, message.member)) return message.channel.createMessage(`***${this.client.util.emojis.ERROR} Permission denied.***`);
message.delete(); message.delete();
let momentMilliseconds: number; let momentMilliseconds: number;
@ -43,9 +39,10 @@ export default class Ban extends Command {
const unit = lockLength[1] as unitOfTime.Base; const unit = lockLength[1] as unitOfTime.Base;
momentMilliseconds = moment.duration(length, unit).asMilliseconds(); momentMilliseconds = moment.duration(length, unit).asMilliseconds();
reason = momentMilliseconds ? args.slice(2).join(' ') : args.slice(1).join(' '); reason = momentMilliseconds ? args.slice(2).join(' ') : args.slice(1).join(' ');
if (reason.length > 512) return this.error(message.channel, 'Ban reasons cannot be longer than 512 characters.');
} }
await this.client.util.moderation.ban(user, message.member, momentMilliseconds, reason); await this.client.util.moderation.ban(user, message.member, momentMilliseconds, reason);
return message.channel.createMessage(`***${this.client.util.emojis.SUCCESS} ${user.username}#${user.id} has been banned.***`); return this.success(message.channel, `${user.username}#${user.id} has been banned.`);
} catch (err) { } catch (err) {
return this.client.util.handleError(err, message, this, false); return this.client.util.handleError(err, message, this, false);
} }

View File

@ -54,9 +54,9 @@ export default class Eval extends Command {
if (display[5]) { if (display[5]) {
try { try {
const { data } = await axios.post('https://snippets.cloud.libraryofcode.org/documents', display.join('')); const { data } = await axios.post('https://snippets.cloud.libraryofcode.org/documents', display.join(''));
return message.channel.createMessage(`${this.client.util.emojis.SUCCESS} Your evaluation evaled can be found on https://snippets.cloud.libraryofcode.org/${data.key}`); return this.success(message.channel, `Your evaluation evaled can be found on https://snippets.cloud.libraryofcode.org/${data.key}`);
} catch (error) { } catch (error) {
return message.channel.createMessage(`${this.client.util.emojis.ERROR} ${error}`); return this.error(message.channel, `${error}`);
} }
} }

View File

@ -1,5 +1,5 @@
/* eslint-disable prefer-destructuring */ /* eslint-disable prefer-destructuring */
import { Activity, Member, Message } from 'eris'; import { Activity, Member, Message, PrivateChannel, GroupChannel } from 'eris';
import { Client, Command, RichEmbed } from '../class'; import { Client, Command, RichEmbed } from '../class';
export default class Game extends Command { export default class Game extends Command {
@ -19,10 +19,9 @@ export default class Game extends Command {
let member: Member; let member: Member;
if (!args[0]) member = message.member; if (!args[0]) member = message.member;
else { else {
// @ts-ignore member = this.client.util.resolveMember(args.join(' '), message.member.guild);
member = this.client.util.resolveMember(message, args[0], message.channel.guild);
if (!member) { if (!member) {
return message.channel.createMessage(`***${this.client.util.emojis.ERROR} Member not found.***`); return this.error(message.channel, 'Member not found.');
} }
} }
if (member.activities.length <= 0) return message.channel.createMessage(`***${this.client.util.emojis.ERROR} Cannot find a game for this member.***`); if (member.activities.length <= 0) return message.channel.createMessage(`***${this.client.util.emojis.ERROR} Cannot find a game for this member.***`);
@ -35,7 +34,7 @@ export default class Game extends Command {
mainStatus = member.activities[0]; mainStatus = member.activities[0];
} }
embed.setAuthor(member.user.username, member.user.avatarURL); embed.setAuthor(member.user.username, member.user.avatarURL);
if (mainStatus?.name === 'Spotify') { if (mainStatus.type === 4) {
embed.setTitle('Spotify'); embed.setTitle('Spotify');
embed.setColor('#1ed760'); embed.setColor('#1ed760');
embed.addField('Song', mainStatus.details, true); embed.addField('Song', mainStatus.details, true);
@ -51,7 +50,7 @@ export default class Game extends Command {
embed.setFooter(`Listening to Spotify | ${this.client.user.username}`, 'https://media.discordapp.net/attachments/358674161566220288/496894273304920064/2000px-Spotify_logo_without_text.png'); embed.setFooter(`Listening to Spotify | ${this.client.user.username}`, 'https://media.discordapp.net/attachments/358674161566220288/496894273304920064/2000px-Spotify_logo_without_text.png');
embed.setTimestamp(); embed.setTimestamp();
} else { } else {
return message.channel.createMessage(`***${this.client.util.emojis.ERROR} Only Spotify games are supported at this time.***`); return this.error(message.channel, 'Only Spotify games are supported at this time.');
} }
return message.channel.createMessage({ embed }); return message.channel.createMessage({ embed });
} catch (err) { } catch (err) {

View File

@ -14,19 +14,13 @@ export default class Roleinfo extends Command {
public async run(message: Message, args: string[]) { public async run(message: Message, args: string[]) {
try { try {
if (!args[0]) return message.channel.createMessage(`***${this.client.util.emojis.ERROR} You need to specifiy a role ID or a role name.***`); if (!args[0]) return this.error(message.channel, 'You need to specifiy a role ID or a role name.');
// @ts-ignore let role: Role = message.member.guild.roles.find((r: Role) => r.id === args[0]);
let role: Role = message.channel.guild.roles.find((r: Role) => r.id === args[0]);
if (!role) { // if it's a role name if (!role) { // if it's a role name
// @ts-ignore role = message.member.guild.roles.find((r: Role) => r.name.toLowerCase().includes(args.join(' ').toLowerCase()));
role = message.channel.guild.roles.find((r: Role) => r.name.toLowerCase().includes(args.join(' ').toLowerCase()));
} }
if (!role) return this.client.createMessage(message.channel.id, `***${this.client.util.emojis.ERROR} Could not find role.***`); if (!role) return this.error(message.channel, 'Could not find role.');
const ms = role.createdAt;
const date = new Date(ms).toLocaleDateString('en-us');
const time = new Date(ms).toLocaleTimeString('en-us');
const perms = role.permissions; const perms = role.permissions;
const permsArray: string[] = []; const permsArray: string[] = [];
@ -45,11 +39,11 @@ export default class Roleinfo extends Command {
embed.setDescription(`<@&${role.id}> ID: \`${role.id}\``); embed.setDescription(`<@&${role.id}> ID: \`${role.id}\``);
embed.setColor(role.color); embed.setColor(role.color);
embed.addField('Name', role.name, true); embed.addField('Name', role.name, true);
embed.addField('Color', `#${role.color.toString(16)}`, true); embed.addField('Color', role.color ? this.client.util.decimalToHex(role.color) : 'None', true);
embed.addField('Hoisted', role.hoist.toString(), true); embed.addField('Hoisted', role.hoist ? 'Yes' : 'No', true);
embed.addField('Position', role.position.toString(), true); embed.addField('Position', role.position ? 'Yes' : 'No', true);
embed.addField('Creation Date', `${date} ${time}`, true); embed.addField('Creation Date', new Date(role.createdAt).toLocaleString(), true);
embed.addField('Mentionnable', role.mentionable.toString(), true); embed.addField('Mentionable', role.mentionable ? 'Yes' : 'No', true);
embed.setFooter(this.client.user.username, this.client.user.avatarURL); embed.setFooter(this.client.user.username, this.client.user.avatarURL);
embed.setTimestamp(); embed.setTimestamp();

View File

@ -14,29 +14,21 @@ export default class Unban extends Command {
public async run(message: Message, args: string[]) { public async run(message: Message, args: string[]) {
try { try {
// @ts-ignore
let user: User; let user: User;
try { try {
user = await this.client.getRESTUser(args[0]); user = await this.client.getRESTUser(args[0]);
} catch { } catch {
return message.channel.createMessage(`***${this.client.util.emojis.ERROR} Could find find user.***`); return this.error(message.channel, 'Could find find user.');
}
try {
if (await this.client.getRESTGuildMember(this.client.config.guildID, args[0])) return message.channel.createMessage(`***${this.client.util.emojis.ERROR} This member exists in the server.***`);
} catch {
// eslint-disable-next-line no-unused-expressions
undefined;
} }
try { try {
await this.client.guilds.get(this.client.config.guildID).getBan(args[0]); await this.client.guilds.get(this.client.config.guildID).getBan(args[0]);
} catch { } catch {
return message.channel.createMessage(`***${this.client.util.emojis.ERROR} This user is not banned.***`); return this.error(message.channel, 'This user is not banned.');
} }
if (!user) return message.channel.createMessage(`***${this.client.util.emojis.ERROR} Unable to locate user.***`);
message.delete(); message.delete();
await this.client.util.moderation.unban(user.id, message.member, args.slice(1).join(' ')); await this.client.util.moderation.unban(user.id, message.member, args.slice(1).join(' '));
return message.channel.createMessage(`***${this.client.util.emojis.SUCCESS} ${user.username}#${user.discriminator} has been unbanned.***`); return this.success(message.channel, `${user.username}#${user.discriminator} has been unbanned.`);
} catch (err) { } catch (err) {
return this.client.util.handleError(err, message, this, false); return this.client.util.handleError(err, message, this, false);
} }

View File

@ -1,6 +1,6 @@
/* eslint-disable no-bitwise */ /* eslint-disable no-bitwise */
import moment from 'moment'; import moment from 'moment';
import { Message, Member } from 'eris'; import { Message, Member, PrivateChannel, GroupChannel } from 'eris';
import { Client, Command, RichEmbed } from '../class'; import { Client, Command, RichEmbed } from '../class';
import acknowledgements from '../configs/acknowledgements.json'; import acknowledgements from '../configs/acknowledgements.json';
import { whois as emotes } from '../configs/emotes.json'; import { whois as emotes } from '../configs/emotes.json';
@ -21,11 +21,11 @@ export default class Whois extends Command {
let member: Member; let member: Member;
if (!args[0]) member = message.member; if (!args[0]) member = message.member;
else { else {
// @ts-ignore member = this.client.util.resolveMember(args.join(' '), message.member.guild);
member = this.client.util.resolveMember(args.join(' '), message.channel.guild);
if (!member) {
return message.channel.createMessage(`***${this.client.util.emojis.ERROR} Member not found.***`);
} }
if (!member) {
return this.error(message.channel, 'Member not found.');
} }
const embed = new RichEmbed(); const embed = new RichEmbed();
embed.setAuthor(`${member.user.username}#${member.user.discriminator}`, member.user.avatarURL); embed.setAuthor(`${member.user.username}#${member.user.discriminator}`, member.user.avatarURL);
@ -58,18 +58,15 @@ export default class Whois extends Command {
} }
description += `\n<@${member.id}>`; description += `\n<@${member.id}>`;
embed.setDescription(description); embed.setDescription(description);
// @ts-ignore
for (const role of member.roles.map((r) => message.channel.guild.roles.get(r)).sort((a, b) => b.position - a.position)) { const roles = member.roles.map((r) => message.member.guild.roles.get(r)).sort((a, b) => b.position - a.position);
if (role.color !== 0) {
embed.setColor(role.color); const { color } = roles.find((r) => r.color);
break; embed.setColor(color);
}
}
embed.addField('Status', `${member.status[0].toUpperCase()}${member.status.slice(1)}`, true); embed.addField('Status', `${member.status[0].toUpperCase()}${member.status.slice(1)}`, true);
embed.addField('Joined At', `${moment(new Date(message.member.joinedAt)).format('dddd, MMMM Do YYYY, h:mm:ss A')} ET`, true); embed.addField('Joined At', `${moment(new Date(message.member.joinedAt)).format('dddd, MMMM Do YYYY, h:mm:ss A')} ET`, true);
embed.addField('Created At', `${moment(new Date(message.author.createdAt)).format('dddd, MMMM Do YYYY, h:mm:ss A')} ET`, true); embed.addField('Created At', `${moment(new Date(message.author.createdAt)).format('dddd, MMMM Do YYYY, h:mm:ss A')} ET`, true);
// @ts-ignore embed.addField(`Roles [${roles.length}]`, roles.map((r) => `<@&${r.id}>`).join(', '));
embed.addField(`Roles [${member.roles.length}]`, member.roles.map((r) => message.channel.guild.roles.get(r)).sort((a, b) => b.position - a.position).map((r) => `<@&${r.id}>`).join(', '));
const permissions: string[] = []; const permissions: string[] = [];
const serverAcknowledgements: string[] = []; const serverAcknowledgements: string[] = [];
const bit = member.permission.allow; const bit = member.permission.allow;
@ -101,7 +98,6 @@ export default class Whois extends Command {
} }
public resolveStaffInformation(id: string) { public resolveStaffInformation(id: string) {
const ack = acknowledgements.find((m) => m.id === id); return acknowledgements.find((m) => m.id === id);
return ack;
} }
} }

View File

@ -16,8 +16,8 @@ export default class {
this.client.util.handleError(err); this.client.util.handleError(err);
process.exit(1); process.exit(1);
}); });
process.on('unhandledRejection', (err) => { process.on('unhandledRejection', (err: Error) => {
this.client.util.handleError(new Error(err.toString())); this.client.util.handleError(err);
}); });
} }
} }

View File

@ -2,7 +2,7 @@
"compilerOptions": { "compilerOptions": {
/* Basic Options */ /* Basic Options */
// "incremental": true, /* Enable incremental compilation */ // "incremental": true, /* Enable incremental compilation */
"target": "ES2017", /* Specify ECMAScript target version: 'ES3' (default), 'ES5', 'ES2015', 'ES2016', 'ES2017', 'ES2018', 'ES2019' or 'ESNEXT'. */ "target": "ES2020", /* Specify ECMAScript target version: 'ES3' (default), 'ES5', 'ES2015', 'ES2016', 'ES2017', 'ES2018', 'ES2019' or 'ESNEXT'. */
"module": "commonjs", /* Specify module code generation: 'none', 'commonjs', 'amd', 'system', 'umd', 'es2015', or 'ESNext'. */ "module": "commonjs", /* Specify module code generation: 'none', 'commonjs', 'amd', 'system', 'umd', 'es2015', or 'ESNext'. */
// "lib": [], /* Specify library files to be included in the compilation. */ // "lib": [], /* Specify library files to be included in the compilation. */
// "allowJs": true, /* Allow javascript files to be compiled. */ // "allowJs": true, /* Allow javascript files to be compiled. */