namespace App\Console\Commands;
use App\DiscordAppCommands\AlttpCommand;
+use App\DiscordAppCommands\EventsCommand;
use App\Models\DiscordBotCommand as CommandModel;
use App\Models\DiscordChannel;
use App\Models\DiscordGuild;
use App\Models\DiscordRole;
use Discord\Discord;
use Discord\Parts\Channel\Channel;
-use Discord\Parts\Channel\Message;
use Discord\Parts\Guild\Guild;
use Discord\Parts\Guild\Role;
use Discord\Parts\User\Activity;
use Discord\WebSockets\Intents;
use Illuminate\Console\Command;
use Monolog\Handler\StreamHandler;
+use Monolog\Level;
use Monolog\Logger;
-use React\EventLoop\Loop;
class DiscordBotCommand extends Command
{
public function handle()
{
$logger = new Logger('DiscordBot');
- $logger->pushHandler(new StreamHandler('php://stdout', Logger::INFO));
+ $logger->pushHandler(new StreamHandler('php://stdout', Level::Info));
$discord = new Discord([
'intents' => Intents::getDefaultIntents() | Intents::GUILD_MEMBERS,
'logger' => $logger,
$discord->updatePresence($activity);
$discord->getLoop()->addPeriodicTimer(1, function () use ($discord) {
- $command = CommandModel::where('status', '=', 'pending')->oldest()->first();
+ $command = CommandModel::query()->where('status', '=', 'pending')->oldest()->first();
if ($command) {
$this->line('executing command '.$command->id.': '.$command->command);
try {
if (config('discord.enable_commands')) {
AlttpCommand::listen($discord);
+ EventsCommand::listen($discord);
}
if (config('discord.create_commands')) {
AlttpCommand::create($discord);
+ EventsCommand::create($discord);
}
});
$discord->on(Event::GUILD_CREATE, function (Guild $guild, Discord $discord) {
$this->error('guild role delete: '.$e->getMessage());
}
});
- $discord->getLoop()->addSignal(SIGINT, function() use ($discord) {
+ $discord->getLoop()->addSignal(SIGINT, function () use ($discord) {
$discord->close();
});
$discord->run();
class AlttpCommand {
- public static function create(Discord $discord) {
+ public static function create(Discord $discord): void {
$command = CommandBuilder::new();
$command->setName('alttp');
$command->setDescription('A Link to the Past');
);
}
- public static function listen(Discord $discord) {
+ public static function listen(Discord $discord): void {
AlttpTechCommand::listen('alttp', $discord);
}
use Discord\Builders\MessageBuilder;
use Discord\Discord;
use Discord\Parts\Embed\Embed;
-use Discord\Parts\Embed\Footer;
use Discord\Parts\Interactions\Command\Option;
use Discord\Parts\Interactions\Interaction;
class AlttpTechCommand {
- public static function create(Discord $discord) {
+ public static function create(Discord $discord): Option {
$command = new Option($discord);
$command->setType(Option::SUB_COMMAND);
$command->setName('tech');
return $command;
}
- public static function listen($parent, Discord $discord) {
+ public static function listen(string $parent, Discord $discord): void {
$discord->listenCommand(
[$parent, 'tech'],
function (Interaction $interaction) use ($discord) {
$interaction
->acknowledgeWithResponse()
- ->done(function() use ($discord, $interaction) {
+ ->done(function () use ($discord, $interaction) {
try {
$lang = Technique::locale2lang($interaction->locale);
- $tech = Technique
- ::where('type', '=', 'tech')
+ $tech = Technique::query()
+ ->where('type', '=', 'tech')
->where('name', '=', $interaction->data->options['tech']->options['name']->value)
->firstOrFail();
$properties = [
$properties['image'] = [
'url' => url($tech->gif),
];
- } else if ($tech->image) {
+ } elseif ($tech->image) {
$properties['image'] = [
'url' => url($tech->image),
];
$phrase = $interaction->data->options['tech']->options['name']->value;
} catch (\Exception $e) {
}
- $tech = Technique::where('type', '=', 'tech')->where('index', '=', 1)->whereNotNull('name');
+ $tech = Technique::query()
+ ->where('type', '=', 'tech')
+ ->where('index', '=', 1)
+ ->whereNotNull('name');
if (!empty($phrase)) {
if ($lang == 'en') {
$tech->where('title', 'LIKE', '%'.$phrase.'%');
$tech->orWhere('short', 'LIKE', '%'.$phrase.'%');
} else {
- $tech = $tech->whereHas('translations', function ($query) use ($lang, $phrase) {
+ $tech->whereHas('translations', function ($query) use ($lang, $phrase) {
$query->where('locale', '=', $lang);
$query->where(function ($subquery) use ($phrase) {
$subquery->where('title', 'LIKE', '%'.$phrase.'%');
'name' => $t->getTranslatedProperty('title', $lang),
'value' => $t->name,
];
- if (count($choices) == 25) break;
+ if (count($choices) == 25) {
+ break;
+ }
}
usort($choices, function ($a, $b) use ($phrase) {
$a_head = stripos($a['name'], $phrase) === 0;
--- /dev/null
+<?php
+
+namespace App\DiscordAppCommands;
+
+use Discord\Builders\CommandBuilder;
+use Discord\Discord;
+
+class EventsCommand {
+
+ public static function create(Discord $discord): void {
+ $command = CommandBuilder::new();
+ $command->setName('events');
+ $command->setDescription('Event subscriptions');
+ $command->setDescriptionLocalization('de', 'Event Abonnements');
+ $command->setDmPermission(false);
+ $command->setDefaultMemberPermissions("0");
+ $command->addOption(EventsShowCommand::create($discord));
+ $discord->application->commands->save(
+ $discord->application->commands->create($command->toArray())
+ );
+ }
+
+ public static function listen(Discord $discord): void {
+ EventsShowCommand::listen('events', $discord);
+ }
+
+}
--- /dev/null
+<?php
+
+namespace App\DiscordAppCommands;
+
+use App\Models\DiscordGuild;
+use App\Models\Technique;
+use Discord\Builders\MessageBuilder;
+use Discord\Discord;
+use Discord\Parts\Interactions\Command\Option;
+use Discord\Parts\Interactions\Interaction;
+
+class EventsShowCommand {
+
+ public static function create(Discord $discord): Option {
+ $command = new Option($discord);
+ $command->setType(Option::SUB_COMMAND);
+ $command->setName('show');
+ $command->setDescription('Show what events your server subscribes to on alttp.localhorst.tv');
+ return $command;
+ }
+
+ public static function listen(string $parent, Discord $discord): void {
+ $discord->listenCommand(
+ [$parent, 'show'],
+ function (Interaction $interaction) use ($discord) {
+ $interaction
+ ->acknowledgeWithResponse()
+ ->done(function () use ($discord, $interaction) {
+ try {
+ // TODO: translation
+ $lang = Technique::locale2lang($interaction->locale);
+ $guild = DiscordGuild::query()->where('guild_id', '=', $interaction->guild_id)->firstOrFail();
+ $embed = $guild->getSubscriptionsEmbed($discord);
+ $message = MessageBuilder::new();
+ $message->addEmbed($embed);
+ $interaction->updateOriginalResponse($message);
+ } catch (\Throwable $e) {
+ $message = MessageBuilder::new();
+ $message->setContent('Error: '.$e->getMessage());
+ $interaction->updateOriginalResponse($message);
+ }
+ });
+ },
+ );
+ }
+
+}
namespace App\Models;
+use Discord\Discord;
+use Discord\Parts\Embed\Embed;
use Discord\Parts\Guild\Guild;
use Illuminate\Database\Eloquent\Factories\HasFactory;
use Illuminate\Database\Eloquent\Model;
-class DiscordGuild extends Model
-{
+class DiscordGuild extends Model {
use HasFactory;
- public static function onUpstreamCreate(Guild $guild) {
+ public static function onUpstreamCreate(Guild $guild): void {
static::sync($guild);
}
- public static function onUpstreamUpdate(Guild $guild) {
+ public static function onUpstreamUpdate(Guild $guild): void {
static::sync($guild);
}
- public static function sync(Guild $guild) {
+ public static function sync(Guild $guild): void {
$model = static::firstOrNew([
'guild_id' => $guild->id,
]);
return $this->hasMany(DiscordGuildUserSubscription::class);
}
+
+ public function getSubscriptionsEmbed(Discord $discord): Embed {
+ $any = count($this->event_subscriptions) + count($this->ladder_subscriptions) + count($this->user_subscriptions);
+ $title = 'Creating events for:';
+ $text = '';
+ if (count($this->event_subscriptions)) {
+ $text .= "Events:\n";
+ foreach ($this->event_subscriptions as $esub) {
+ $text .= '- ['.$esub->event->title.']('.$esub->event->getURL().")\n";
+ }
+ $text .= "\n";
+ }
+ if (count($this->ladder_subscriptions)) {
+ $text .= "Ladder Modes:\n";
+ foreach ($this->ladder_subscriptions as $lsub) {
+ $text .= '- '.$lsub->step_ladder_mode->name.' ('.substr($lsub->step_ladder_mode->ext_id, 11).")\n";
+ }
+ $text .= "\n";
+ }
+ if (count($this->user_subscriptions)) {
+ $text .= "Runners:\n";
+ foreach ($this->user_subscriptions as $usub) {
+ $text .= '- '.$usub->user->getName()."\n";
+ }
+ $text .= "\n";
+ }
+ if (empty($text)) {
+ $text = 'Nothing, really';
+ }
+ $properties = [
+ 'color' => 0x389c38,
+ 'description' => $text,
+ 'title' => $title,
+ 'type' => 'rich',
+ ];
+ return new Embed($discord, $properties);
+ }
+
+
protected $fillable = [
'guild_id',
];
return '';
}
+ public function getURL(): string {
+ return url('/events/'.$this->name);
+ }
+
protected $casts = [
'end' => 'datetime',
'start' => 'datetime',