2020-04-14 21:33:34 -04:00
import signale from 'signale' ;
2020-04-15 12:19:46 -04:00
import { Member , Message , Guild , PrivateChannel , GroupChannel , Role , AnyGuildChannel } from 'eris' ;
2020-04-15 15:13:44 -04:00
import { Client , Command , Moderation , RichEmbed } from '.' ;
2020-04-14 21:18:44 -04:00
import { statusMessages as emotes } from '../configs/emotes.json' ;
2020-04-14 13:15:33 -04:00
export default class Util {
public client : Client ;
2020-04-15 15:13:44 -04:00
public moderation : Moderation ;
2020-04-14 21:33:34 -04:00
public signale : signale.Signale ;
2020-04-14 13:15:33 -04:00
constructor ( client : Client ) {
this . client = client ;
2020-04-15 15:13:44 -04:00
this . moderation = new Moderation ( this . client ) ;
2020-04-14 21:33:34 -04:00
this . signale = signale ;
this . signale . config ( {
displayDate : true ,
displayTimestamp : true ,
displayFilename : true ,
} ) ;
2020-04-14 13:15:33 -04:00
}
get emojis() {
return {
2020-04-14 21:18:44 -04:00
SUCCESS : emotes.success ,
LOADING : emotes.loading ,
ERROR : emotes.error ,
2020-04-14 13:15:33 -04:00
} ;
}
/ * *
* Resolves a command
* @param query Command input
* @param message Only used to check for errors
* /
public resolveCommand ( query : string | string [ ] ) : Promise < { cmd : Command , args : string [ ] } > {
try {
// let resolvedCommand: Command;
// eslint-disable-next-line no-param-reassign
if ( typeof query === 'string' ) query = query . split ( ' ' ) ;
const commands = this . client . commands . toArray ( ) ;
const resolvedCommand = commands . find ( ( c ) = > c . name === query [ 0 ] . toLowerCase ( ) || c . aliases . includes ( query [ 0 ] . toLowerCase ( ) ) ) ;
if ( ! resolvedCommand ) return Promise . resolve ( null ) ;
query . shift ( ) ;
return Promise . resolve ( { cmd : resolvedCommand , args : query } ) ;
} catch ( error ) {
return Promise . reject ( error ) ;
}
}
2020-04-14 19:03:10 -04:00
2020-04-15 12:19:46 -04:00
public resolveGuildChannel ( query : string , { channels } : Guild ) : AnyGuildChannel | undefined {
let queries = query . split ( ' ' ) . slice ( 0 , 10 ) . join ( ' ' ) ;
2020-04-15 15:13:44 -04:00
const nchannels = channels . map ( ( c ) = > c ) . sort ( ( a : AnyGuildChannel , b : AnyGuildChannel ) = > a . type - b . type ) ;
2020-04-15 12:19:46 -04:00
let channel = nchannels . find ( ( c ) = > ( c . id === queries || c . name === queries || c . name . toLowerCase ( ) === queries . toLowerCase ( ) || c . name . toLowerCase ( ) . startsWith ( queries . toLowerCase ( ) ) ) ) ;
if ( ! channel && queries . split ( ' ' ) . length > 0 ) {
while ( ! channel && queries . split ( ' ' ) . length > 1 ) {
queries = queries . split ( ' ' ) . slice ( 0 , queries . split ( ' ' ) . length - 1 ) . join ( ' ' ) ;
// eslint-disable-next-line no-loop-func
channel = nchannels . find ( ( c ) = > c . id === queries || c . name === queries || c . name . toLowerCase ( ) === queries . toLowerCase ( ) || c . name . toLowerCase ( ) . startsWith ( queries . toLowerCase ( ) ) ) ;
}
}
return channel ;
}
2020-04-15 11:57:37 -04:00
public resolveRole ( query : string , { roles } : Guild ) : Role | undefined {
let queries = query . split ( ' ' ) . slice ( 0 , 10 ) . join ( ' ' ) ;
let role = roles . find ( ( r ) = > r . id === queries || r . name === queries || r . name . toLowerCase ( ) === queries . toLowerCase ( ) || r . name . toLowerCase ( ) . startsWith ( queries . toLowerCase ( ) ) ) ;
if ( ! role && queries . split ( ' ' ) . length > 0 ) {
while ( ! role && queries . split ( ' ' ) . length > 1 ) {
queries = queries . split ( ' ' ) . slice ( 0 , queries . split ( ' ' ) . length - 1 ) . join ( ' ' ) ;
2020-04-15 12:02:13 -04:00
// eslint-disable-next-line no-loop-func
2020-04-15 11:57:37 -04:00
role = roles . find ( ( r ) = > r . id === queries || r . name === queries || r . name . toLowerCase ( ) === queries . toLowerCase ( ) || r . name . toLowerCase ( ) . startsWith ( queries . toLowerCase ( ) ) ) ;
}
}
return role ;
}
2020-04-15 11:15:50 -04:00
public resolveMember ( query : string , { members } : Guild ) : Member | undefined {
2020-04-15 11:42:08 -04:00
let queries = query . split ( ' ' ) . slice ( 0 , 10 ) . join ( ' ' ) ;
let member = members . find ( ( m ) = > m . mention . replace ( '!' , '' ) === queries . replace ( '!' , '' ) || ` ${ m . username } # ${ m . discriminator } ` === query || m . username === queries || m . id === queries || m . nick === queries ) // Exact match for mention, username+discrim, username and user ID
|| members . find ( ( m ) = > ` ${ m . username . toLowerCase ( ) } # ${ m . discriminator } ` === queries . toLowerCase ( ) || m . username . toLowerCase ( ) === queries . toLowerCase ( ) || ( m . nick && m . nick . toLowerCase ( ) === queries . toLowerCase ( ) ) ) // Case insensitive match for username+discrim, username
|| members . find ( ( m ) = > m . username . toLowerCase ( ) . startsWith ( queries . toLowerCase ( ) ) || ( m . nick && m . nick . toLowerCase ( ) . startsWith ( queries . toLowerCase ( ) ) ) ) ;
2020-04-15 11:59:22 -04:00
if ( queries . split ( ' ' ) . length > 1 && ! member ) {
while ( ! member && queries . split ( ' ' ) . length > 0 ) {
2020-04-15 11:42:08 -04:00
queries = queries . split ( ' ' ) . slice ( 0 , queries . length - 1 ) . join ( ' ' ) ;
2020-04-15 12:02:13 -04:00
// eslint-disable-next-line no-loop-func
2020-04-15 11:42:08 -04:00
member = members . find ( ( m ) = > m . mention . replace ( '!' , '' ) === queries . replace ( '!' , '' ) || ` ${ m . username } # ${ m . discriminator } ` === query || m . username === queries || m . id === queries || m . nick === queries ) // Exact match for mention, username+discrim, username and user ID
2020-04-15 15:13:44 -04:00
// eslint-disable-next-line no-loop-func
2020-04-15 11:42:08 -04:00
|| members . find ( ( m ) = > ` ${ m . username . toLowerCase ( ) } # ${ m . discriminator } ` === queries . toLowerCase ( ) || m . username . toLowerCase ( ) === queries . toLowerCase ( ) || ( m . nick && m . nick . toLowerCase ( ) === queries . toLowerCase ( ) ) ) // Case insensitive match for username+discrim, username
2020-04-15 15:13:44 -04:00
// eslint-disable-next-line no-loop-func
2020-04-15 11:42:08 -04:00
|| members . find ( ( m ) = > m . username . toLowerCase ( ) . startsWith ( queries . toLowerCase ( ) ) || ( m . nick && m . nick . toLowerCase ( ) . startsWith ( queries . toLowerCase ( ) ) ) ) ;
}
}
return member ;
2020-04-14 19:03:10 -04:00
}
2020-04-14 21:33:34 -04:00
2020-04-15 15:33:27 -04:00
public async handleError ( error : Error , message? : Message , command? : Command , disable? : boolean ) : Promise < void > {
2020-04-14 21:33:34 -04:00
try {
this . signale . error ( error ) ;
const info = { content : ` \` \` \` js \ n ${ error . stack } \ n \` \` \` ` , embed : null } ;
if ( message ) {
const embed = new RichEmbed ( ) ;
embed . setColor ( 'FF0000' ) ;
embed . setAuthor ( ` Error caused by ${ message . author . username } # ${ message . author . discriminator } ` , message . author . avatarURL ) ;
embed . setTitle ( 'Message content' ) ;
embed . setDescription ( message . content ) ;
embed . addField ( 'User' , ` ${ message . author . mention } ( \` ${ message . author . id } \` ) ` , true ) ;
embed . addField ( 'Channel' , message . channel . mention , true ) ;
let guild : string ;
if ( message . channel instanceof PrivateChannel || message . channel instanceof GroupChannel ) guild = '@me' ;
else guild = message . channel . guild . id ;
embed . addField ( 'Message link' , ` [Click here](https://discordapp.com/channels/ ${ guild } / ${ message . channel . id } / ${ message . id } ) ` , true ) ;
embed . setTimestamp ( new Date ( message . timestamp ) ) ;
info . embed = embed ;
}
await this . client . createMessage ( '595788220764127272' , info ) ;
const msg = message . content . slice ( this . client . config . prefix . length ) . trim ( ) . split ( / +/g ) ;
// eslint-disable-next-line no-param-reassign
2020-04-15 15:33:27 -04:00
if ( command && disable ) this . resolveCommand ( msg ) . then ( ( c ) = > { c . cmd . enabled = false ; } ) ;
2020-04-14 21:33:34 -04:00
if ( message ) message . channel . createMessage ( ` *** ${ this . emojis . ERROR } An unexpected error has occured - please contact a Faculty Marshal. ${ command ? ' This command has been disabled.' : '' } *** ` ) ;
} catch ( err ) {
this . signale . error ( err ) ;
}
}
2020-04-15 15:13:44 -04:00
public splitString ( string : string , length : number ) : string [ ] {
if ( ! string ) return [ ] ;
// eslint-disable-next-line no-param-reassign
if ( Array . isArray ( string ) ) string = string . join ( '\n' ) ;
if ( string . length <= length ) return [ string ] ;
const arrayString : string [ ] = [ ] ;
let str : string = '' ;
let pos : number ;
while ( string . length > 0 ) {
pos = string . length > length ? string . lastIndexOf ( '\n' , length ) : string . length ;
if ( pos > length ) pos = length ;
str = string . substr ( 0 , pos ) ;
// eslint-disable-next-line no-param-reassign
string = string . substr ( pos ) ;
arrayString . push ( str ) ;
}
return arrayString ;
}
2020-04-14 13:15:33 -04:00
}