2024-12-28 14:04:25 +00:00
const { SlashCommandBuilder , MessageFlags , EmbedBuilder } = require ( 'discord.js' ) ;
const { Tournament } = require ( "../../data_objects/tournament.js" ) ;
const { tetrioRanks } = require ( "../../data_objects/tetrio_ranks.js" ) ;
const { xhr , reactionCheck , unreactionCheck , updateTournamentsJSON } = require ( "../../utils.js" ) ;
const { tournaments , blacklist , whitelist , trackedTournaments } = require ( "../../index.js" ) ;
module . exports = {
data : new SlashCommandBuilder ( )
. setName ( 'create_event' )
. setDescription ( 'Создать событие, доступное для регистрации' )
. addStringOption ( option =>
option . setName ( 'title' )
. setDescription ( 'Название события' )
. setRequired ( true ) )
. addIntegerOption ( option =>
option . setName ( 'unix_registration_end' )
. setDescription ( 'Время завершения регистрации в формате UNIX времени' )
. setRequired ( true ) )
. addIntegerOption ( option =>
option . setName ( 'unix_checkin_start' )
. setDescription ( 'Время старта checkin в формате UNIX времени' )
. setRequired ( true ) )
. addIntegerOption ( option =>
option . setName ( 'unix_checkin_end' )
. setDescription ( 'Время завершения checkin в формате UNIX времени' )
. setRequired ( true ) )
. addIntegerOption ( option =>
option . setName ( 'unix_tournament_start' )
. setDescription ( 'Время планируемого старта турнира в формате UNIX времени' )
. setRequired ( true ) )
. addStringOption ( option =>
option . setName ( 'description' )
. setDescription ( 'Описание события' ) )
. addStringOption ( option =>
option . setName ( 'prize_pool' )
. setDescription ( 'Призовой фонд турнира' ) )
. addStringOption ( option =>
option . setName ( 'rank_floor' )
. setDescription ( 'Минимальный ранг для участия' ) )
. addStringOption ( option =>
option . setName ( 'rank_roof' )
. setDescription ( 'Максимальный ранг для участия' ) )
. addBooleanOption ( option =>
option . setName ( 'international' )
. setDescription ( 'Данный турнир международный' ) ) ,
async execute ( interaction ) {
await interaction . deferReply ( { flags : MessageFlags . Ephemeral } ) ;
const teto = new Tournament (
interaction . options . getString ( 'title' ) ,
interaction . options . getInteger ( 'unix_registration_end' ) ,
interaction . options . getInteger ( 'unix_checkin_start' ) ,
interaction . options . getInteger ( 'unix_checkin_end' ) ,
interaction . options . getInteger ( 'unix_tournament_start' ) ,
interaction . options . getString ( 'rank_floor' ) ? ? null ,
interaction . options . getString ( 'rank_roof' ) ? ? null ,
interaction . options . getBoolean ( 'international' ) ? ? null ,
interaction . options . getString ( 'description' ) ? ? null ,
interaction . options . getString ( 'prize_pool' ) ? ? null ,
) ;
// Checking, if Tournament information is valid
const current _time = Date . now ( ) / 1000 ;
if ( teto . unix _reg _end < current _time ) {
const exampleEmbed = new EmbedBuilder ( )
. setColor ( 0xFF0000 )
. setTitle ( 'Некорректная информация о турнире' )
. setDescription ( 'Время завершения регистрации уже наступило' )
. setTimestamp ( )
interaction . followUp ( { embeds : [ exampleEmbed ] , flags : MessageFlags . Ephemeral } ) . then ( msg => {
setTimeout ( ( ) => msg . delete ( ) , 10000 )
} ) ;
return
}
if ( teto . unix _checkin _end < current _time ) {
const exampleEmbed = new EmbedBuilder ( )
. setColor ( 0xFF0000 )
. setTitle ( 'Некорректная информация о турнире' )
. setDescription ( 'Время завершения checkin уже наступило' )
. setTimestamp ( )
interaction . followUp ( { embeds : [ exampleEmbed ] , flags : MessageFlags . Ephemeral } ) . then ( msg => {
setTimeout ( ( ) => msg . delete ( ) , 10000 )
} ) ;
return
}
if ( teto . unix _tournament _start < current _time ) {
const exampleEmbed = new EmbedBuilder ( )
. setColor ( 0xFF0000 )
. setTitle ( 'Некорректная информация о турнире' )
. setDescription ( 'Время старта турнира уже наступило' )
. setTimestamp ( )
interaction . followUp ( { embeds : [ exampleEmbed ] , flags : MessageFlags . Ephemeral } ) . then ( msg => {
setTimeout ( ( ) => msg . delete ( ) , 10000 )
} ) ;
return
}
if ( teto . rank _floor !== null && ! tetrioRanks . includes ( teto . rank _floor . toLowerCase ( ) ) ) {
const exampleEmbed = new EmbedBuilder ( )
. setColor ( 0xFF0000 )
. setTitle ( 'Некорректная информация о турнире' )
. setDescription ( ` Нет такого ранга ${ teto . rank _floor } ` )
. setTimestamp ( )
interaction . followUp ( { embeds : [ exampleEmbed ] , flags : MessageFlags . Ephemeral } ) . then ( msg => {
setTimeout ( ( ) => msg . delete ( ) , 10000 )
} ) ;
return
}
if ( teto . rank _roof !== null && ! tetrioRanks . includes ( teto . rank _roof . toLowerCase ( ) ) ) {
const exampleEmbed = new EmbedBuilder ( )
. setColor ( 0xFF0000 )
. setTitle ( 'Некорректная информация о турнире' )
. setDescription ( ` Нет такого ранга ${ teto . rank _roof } ` )
. setTimestamp ( )
interaction . followUp ( { embeds : [ exampleEmbed ] , flags : MessageFlags . Ephemeral } ) . then ( msg => {
setTimeout ( ( ) => msg . delete ( ) , 10000 )
} ) ;
return
}
const reg _role = await interaction . guild . roles . create (
{
name : ` Регистрант на ${ teto . title } ` ,
reason : 'Роль необходима для отслеживания регистрантов турнира' ,
permissions : 0 n
}
) ;
const check _in _role = await interaction . guild . roles . create (
{
name : ` Участник ${ teto . title } ` ,
reason : 'Роль необходима для отслеживания участников турнира' ,
permissions : 0 n
}
) ;
teto . setRoles ( reg _role . id , check _in _role . id ) ;
tournaments . set ( current _time . toString ( ) , teto ) ;
const tournamentEmbed = new EmbedBuilder ( )
. setColor ( 0x00FF00 )
. setTitle ( teto . title )
. setDescription ( ` ${ teto . description ? ` ${ teto . description } \n ` : "" } ${ teto . international ? "Международный" : "Только для игроков из стран СНГ" } ${ teto . prize _pool ? ` \n **Призовой фонд: ${ teto . prize _pool } ** ` : "" } ${ teto . rank _floor ? ` \n Минимальный ранг для участия: ${ teto . rank _floor } ` : "" } ${ teto . rank _roof ? ` \n Максимальный ранг для участия: ${ teto . rank _roof } ` : "" } ` )
. setFooter ( { text : 'Поставьте ✅, чтобы зарегистрироваться' } )
. addFields (
{ name : "Завершение регистрации" , value : ` <t: ${ teto . unix _reg _end } :f> \n (<t: ${ teto . unix _reg _end } :R>) ` } ,
{ name : "Check in" , value : ` <t: ${ teto . unix _checkin _start } :f> \n (<t: ${ teto . unix _checkin _start } :R>) ` } ,
{ name : "Завершение check in" , value : ` <t: ${ teto . unix _checkin _end } :f> \n (<t: ${ teto . unix _checkin _end } :R>) ` } ,
{ name : "**Старт турнира**" , value : ` <t: ${ teto . unix _start } :f> \n (<t: ${ teto . unix _start } :R>) ` } ,
) ;
// Send a message into the channel where command was triggered from
const message = await interaction . followUp ( { embeds : [ tournamentEmbed ] , fetchReply : true } ) ;
message . react ( '✅' ) ;
updateTournamentsJSON ( ) ;
trackedTournaments . push ( current _time . toString ( ) ) ;
2025-01-09 17:28:12 +00:00
teto . setMessageID ( message . id , message . channel . id ) ;
2024-12-28 14:04:25 +00:00
const collectorFilter = ( reaction , user ) => {
return reaction . emoji . name === '✅' && user . id !== message . author . id ;
} ;
// We gonna make sure, that user is eligible for a participation
2025-01-09 17:28:12 +00:00
// NOTE: only 24,855127314815 days max
2024-12-28 14:04:25 +00:00
const collector = message . createReactionCollector ( { filter : collectorFilter , time : teto . unix _reg _end * 1000 - current _time * 1000 , dispose : true } ) ;
collector . on ( 'collect' , async ( reaction , user ) => reactionCheck ( reaction , user , interaction . client , interaction . guild , teto , reg _role ) ) ;
collector . on ( 'remove' , async ( reaction , user ) => unreactionCheck ( reaction , user , interaction . guild , teto , reg _role ) ) ;
} ,
} ;