diff --git a/app/Data/Discord/Component/ActionRowData.php b/app/Data/Discord/Component/ActionRowData.php new file mode 100644 index 0000000..af9c9f8 --- /dev/null +++ b/app/Data/Discord/Component/ActionRowData.php @@ -0,0 +1,19 @@ +|Collection */ + public readonly Collection $components, + public readonly int $type = 1, + ) {} +} diff --git a/app/Data/Discord/Component/ButtonData.php b/app/Data/Discord/Component/ButtonData.php new file mode 100644 index 0000000..5719e28 --- /dev/null +++ b/app/Data/Discord/Component/ButtonData.php @@ -0,0 +1,61 @@ +emoji, '<') && str_contains($ticketButton->emoji, '>')) { + $discordEmoji = str_replace('<', '', $ticketButton->emoji); + $discordEmoji = str_replace('>', '', $discordEmoji); + [$emojiName, $emojiId] = explode(':', $discordEmoji); + + return new self( + name: $emojiName, + id: $emojiId, + ); + } + + return new self( + name: $ticketButton->emoji, + ); + } +} diff --git a/app/Data/Discord/Component/StringCollectorData.php b/app/Data/Discord/Component/StringCollectorData.php new file mode 100644 index 0000000..083c721 --- /dev/null +++ b/app/Data/Discord/Component/StringCollectorData.php @@ -0,0 +1,23 @@ + $options */ + public readonly Collection $options, + public readonly string $placeholder, + public readonly int $min_values, + public readonly int $max_values, + public readonly int $type = 3, + ) {} +} diff --git a/app/Data/Discord/Component/StringCollectorOptionData.php b/app/Data/Discord/Component/StringCollectorOptionData.php new file mode 100644 index 0000000..2ea45a8 --- /dev/null +++ b/app/Data/Discord/Component/StringCollectorOptionData.php @@ -0,0 +1,29 @@ +name, + "{$applicationResponse->id}", + Str::limit($applicationResponse->response, 90), + ); + } +} diff --git a/app/Data/Discord/Embed/EmbedData.php b/app/Data/Discord/Embed/EmbedData.php new file mode 100644 index 0000000..16cd5d1 --- /dev/null +++ b/app/Data/Discord/Embed/EmbedData.php @@ -0,0 +1,23 @@ + $fields */ + public readonly ?Collection $fields = null, + public readonly ?string $timestamp = null, + public readonly ?ThumbnailData $thumbnail = null, + ) {} +} diff --git a/app/Data/Discord/Embed/FieldsData.php b/app/Data/Discord/Embed/FieldsData.php new file mode 100644 index 0000000..ebd2165 --- /dev/null +++ b/app/Data/Discord/Embed/FieldsData.php @@ -0,0 +1,18 @@ +embed_title || ! $application->embed_description || ! $application->embed_color || - ! $application->embed_channel_id + ! $application->embed_channel_id || + ! $application->embed_button_color || + ! $application->embed_button_text ) { return false; } + $data = [ 'embeds' => [ - [ - 'title' => $application->embed_title, - 'description' => $application->embed_description, - 'color' => hexdec(str_replace('#', '', $application->embed_color)), - ], + new EmbedData( + title: $application->embed_title, + description: $application->embed_description, + color: (string) hexdec(str_replace('#', '', $application->embed_color)), + ), ], 'components' => [ - [ - 'type' => 1, - 'components' => [[ - 'type' => 2, // button - 'custom_id' => 'applicationSubmission-start-'.$application->id, - 'style' => $application->embed_button_color, - 'label' => $application->embed_button_text, - ]], - ], + new ActionRowData( + components: collect([ + new ButtonData( + custom_id: 'applicationSubmission-start-'.$application->id, + style: $application->embed_button_color, + label: $application->embed_button_text, + ), + ]) + ), ], ]; $response = Http::discordBot()->post('/channels/'.$application->embed_channel_id.'/messages', $data); diff --git a/app/Http/Controllers/ServerContentController.php b/app/Http/Controllers/ServerContentController.php index cc68c42..7449ff2 100644 --- a/app/Http/Controllers/ServerContentController.php +++ b/app/Http/Controllers/ServerContentController.php @@ -141,13 +141,9 @@ public function resend(ResendServerContentRequest $request): bool */ private function getMessages(string $message, Collection $serverContents): array { - $mapFunction = function ($data) { - return '- ['.$data['name'].']('.$data['url'].")\n - ".$data['description']; - }; - $messages = [ $message, - ...array_map($mapFunction, $serverContents->toArray()), + ...$serverContents->map(fn ($data) => '- ['.$data['name'].']('.$data['url'].")\n - ".$data['description']), ]; $chunkedMessages = ['']; $key = 0; diff --git a/app/Repositories/ApplicationSubmissionRepository.php b/app/Repositories/ApplicationSubmissionRepository.php index 5b688a5..ae2c54a 100644 --- a/app/Repositories/ApplicationSubmissionRepository.php +++ b/app/Repositories/ApplicationSubmissionRepository.php @@ -2,14 +2,20 @@ namespace App\Repositories; +use App\Data\Discord\Component\ActionRowData; +use App\Data\Discord\Component\ButtonData; +use App\Data\Discord\Component\StringCollectorData; +use App\Data\Discord\Component\StringCollectorOptionData; +use App\Data\Discord\Embed\EmbedData; +use App\Data\Discord\Embed\FieldsData; +use App\Data\Discord\Embed\ThumbnailData; use App\Data\Discord\MemberData; use App\Enums\ApplicationSubmissionState; -use App\Enums\DiscordButton; use App\Models\ApplicationSubmission; use Illuminate\Support\Carbon; +use Illuminate\Support\Collection; use Illuminate\Support\Facades\Http; use Illuminate\Support\Facades\Log; -use Illuminate\Support\Str; class ApplicationSubmissionRepository { @@ -92,37 +98,8 @@ public function updateApplicationSubmission(ApplicationSubmission $applicationSu /** * @return array{ - * embeds: array, - * components: \Illuminate\Support\Collection< - * int, - * non-empty-array{ - * type?: int, - * components?: array - * }|non-empty-array{ - * type?: int, - * components?: array, - * placeholder: string, - * min_values: int, - * max_values: int, - * }> - * }> + * embeds: Collection, + * components: Collection * } */ private function getMessageData(ApplicationSubmission $applicationSubmission): array @@ -131,27 +108,15 @@ private function getMessageData(ApplicationSubmission $applicationSubmission): a $buttonActionRow = $this->getButtonsActionRow($applicationSubmission); $acceptActionRow = $this->getAcceptActionRow($applicationSubmission); $denyActionRow = $this->getDenyActionRow($applicationSubmission); - $components = collect([$buttonActionRow, $acceptActionRow, $denyActionRow])->filter(fn ($component) => ! empty($component))->values(); + $components = collect([$buttonActionRow, $acceptActionRow, $denyActionRow])->filter(fn ($component) => $component !== null)->values(); return [ - 'embeds' => [$embed], + 'embeds' => collect([$embed]), 'components' => $components, ]; } - /** - * @return array{ - * title: string, - * fields: array{array{ - * name: string, - * value: string - * }}, - * timestamp: string, - * color: string, - * thumbnail: array{url: string} - * } - */ - private function getSubmissionEmbed(ApplicationSubmission $applicationSubmission): array + private function getSubmissionEmbed(ApplicationSubmission $applicationSubmission): EmbedData { $member = $this->getMember($applicationSubmission); $statsField = $this->getStatsField($applicationSubmission, $member); @@ -172,22 +137,21 @@ private function getSubmissionEmbed(ApplicationSubmission $applicationSubmission $index = ((int) $member->user?->id >> 22) % 6; $avatar = "https://cdn.discordapp.com/embed/avatars/{$index}.png"; } + $thumbnail = new ThumbnailData($avatar); if ($applicationQuestionAnswers->count() > 25) { - return [ - 'title' => $title, - 'description' => "Application Number: **{$applicationSubmissionCount}**", - 'fields' => [$tooLongField, $statsField], - 'timestamp' => now()->toIso8601String(), - 'color' => $this->getEmbedColor($applicationSubmission), - 'thumbnail' => [ - 'url' => $avatar, - ], - ]; + return new EmbedData( + title: $title, + description: "Application Number: **{$applicationSubmissionCount}**", + color: $this->getEmbedColor($applicationSubmission), + fields: collect([$tooLongField, $statsField]), + timestamp: now()->toIso8601String(), + thumbnail: $thumbnail, + ); } $totalLenght = 0; - $fields = []; + $fields = collect([]); $applicationSubmission->applicationQuestionAnswers->each(function ($applicationQuestionAnswer) use (&$fields, &$totalLenght) { $answer = strlen($applicationQuestionAnswer->answer) < 1024 ? @@ -198,42 +162,38 @@ private function getSubmissionEmbed(ApplicationSubmission $applicationSubmission $totalLenght += strlen($answer); $totalLenght += strlen($question); - $fields[] = [ - 'name' => "**{$applicationQuestionAnswer->applicationQuestion?->order}. {$question}**", - 'value' => $answer, - ]; + $fields->push(new FieldsData( + name: "**{$applicationQuestionAnswer->applicationQuestion?->order}. {$question}**", + value: $answer, + )); }); - $totalLenght += strlen($statsField['name']); - $totalLenght += strlen($statsField['value']); + $totalLenght += strlen($statsField->name); + $totalLenght += strlen($statsField->value); - $fields[] = $statsField; + $fields->push($statsField); $totalLenght += strlen($title); if ($totalLenght > 6000) { - return [ - 'title' => $title, - 'description' => "Application Number: **{$applicationSubmissionCount}**", - 'fields' => [$tooLongField, $statsField], - 'timestamp' => now()->toIso8601String(), - 'color' => $this->getEmbedColor($applicationSubmission), - 'thumbnail' => [ - 'url' => $avatar, - ], - ]; + return new EmbedData( + title: $title, + description: "Application Number: **{$applicationSubmissionCount}**", + color: $this->getEmbedColor($applicationSubmission), + fields: collect([$tooLongField, $statsField]), + timestamp: now()->toIso8601String(), + thumbnail: $thumbnail, + ); } - return [ - 'title' => $title, - 'description' => "Application Number: **{$applicationSubmissionCount}**", - 'fields' => $fields, - 'timestamp' => now()->toIso8601String(), - 'color' => $this->getEmbedColor($applicationSubmission), - 'thumbnail' => [ - 'url' => $avatar, - ], - ]; + return new EmbedData( + title: $title, + description: "Application Number: **{$applicationSubmissionCount}**", + color: $this->getEmbedColor($applicationSubmission), + fields: $fields, + timestamp: now()->toIso8601String(), + thumbnail: $thumbnail, + ); } public function getMember(ApplicationSubmission $applicationSubmission): MemberData @@ -258,10 +218,7 @@ public function getEmbedColor(ApplicationSubmission $applicationSubmission): str }; } - /** - * @return array{name:string, value:string} - */ - private function getStatsField(ApplicationSubmission $applicationSubmission, MemberData $member): array + private function getStatsField(ApplicationSubmission $applicationSubmission, MemberData $member): FieldsData { $applicationSubmissionCount = ApplicationSubmission::completed() ->where('discord_id', $applicationSubmission->discord_id) @@ -282,75 +239,49 @@ private function getStatsField(ApplicationSubmission $applicationSubmission, Mem "**Application Number:** {$applicationSubmissionCount}"; $statsTitle = 'Application Stats:'; - return [ - 'name' => $statsTitle, - 'value' => $stats, - ]; + return new FieldsData( + name: $statsTitle, + value: $stats, + ); } - /** - * @return array{name:string, value:string} - */ - private function getTooLongField(): array + private function getTooLongField(): FieldsData { - return [ - 'name' => '**Application too long**', - 'value' => 'Please view the application on the thread', - ]; + return new FieldsData( + name: '**Application too long**', + value: 'Please view the application on the thread', + ); } - /** - * @return array{ - * type?: int, - * components?: array - * } - */ - private function getButtonsActionRow(ApplicationSubmission $applicationSubmission): array + private function getButtonsActionRow(ApplicationSubmission $applicationSubmission): ActionRowData { $buttons = collect(); if ($applicationSubmission->state === ApplicationSubmissionState::Pending) { - $buttons->push([ - 'type' => 2, // button - 'custom_id' => 'applicationSubmission-accept-'.$applicationSubmission->id, - 'style' => DiscordButton::Success, - 'label' => 'Accept', - ]); - $buttons->push([ - 'type' => 2, // button - 'custom_id' => 'applicationSubmission-deny-'.$applicationSubmission->id, - 'style' => DiscordButton::Danger, - 'label' => 'Deny', - ]); - $buttons->push([ - 'type' => 2, // button - 'custom_id' => 'applicationSubmission-acceptWithReason-'.$applicationSubmission->id, - 'style' => DiscordButton::Success, - 'label' => 'Accept with reason', - ]); - $buttons->push([ - 'type' => 2, // button - 'custom_id' => 'applicationSubmission-denyWithReason-'.$applicationSubmission->id, - 'style' => DiscordButton::Danger, - 'label' => 'Deny with reason', - ]); + + $buttons->push(ButtonData::success( + 'applicationSubmission-accept-'.$applicationSubmission->id, + 'Accept', + )); + $buttons->push(ButtonData::danger( + 'applicationSubmission-deny-'.$applicationSubmission->id, + 'Deny', + )); + $buttons->push(ButtonData::success( + 'applicationSubmission-acceptWithReason-'.$applicationSubmission->id, + 'Accept with reason', + )); + $buttons->push(ButtonData::danger( + 'applicationSubmission-denyWithReason-'.$applicationSubmission->id, + 'Deny with reason', + )); } - $buttons->push([ - 'type' => 2, // button - 'custom_id' => 'applicationSubmission-history-'.$applicationSubmission->id, - 'style' => DiscordButton::Primary, - 'label' => 'History', - ]); + $buttons->push(ButtonData::primary( + 'applicationSubmission-history-'.$applicationSubmission->id, + 'History', + )); - return [ - 'type' => 1, - 'components' => $buttons->toArray(), - ]; + return new ActionRowData(components: $buttons); } private function sendResponseToUser(ApplicationSubmission $applicationSubmission, string $action): bool @@ -447,6 +378,8 @@ private function createThread(ApplicationSubmission $applicationSubmission): voi $thread = $threadResponse->json(); if (! $threadResponse->created()) { Log::error('Could not create thread:', $thread); + + return; } $applicationSubmission->applicationQuestionAnswers ->each(function ($applicationQuestionAnswer) use ($thread) { @@ -499,85 +432,49 @@ private function chunkTextBySpace(int $limit, string $text): array return $chunks; } - /** - * @return array{ - * type?: int, - * components?: array, - * placeholder: string, - * min_values: int, - * max_values: int, - * }> - * } - */ - private function getAcceptActionRow(ApplicationSubmission $applicationSubmission): array + private function getAcceptActionRow(ApplicationSubmission $applicationSubmission): ?ActionRowData { if ($applicationSubmission->state !== ApplicationSubmissionState::Pending) { - return []; + return null; } - $options = $applicationSubmission->application?->acceptedResponses()->limit(25)->get()->map(fn ($response) => [ - 'label' => $response->name, - 'value' => "{$response->id}", - 'description' => Str::limit($response->response, 90), - ]) ?? collect(); + + /** @var Collection $options */ + $options = StringCollectorOptionData::collect($applicationSubmission->application?->acceptedResponses()->limit(25)->get() ?? []); if ($options->isEmpty()) { - return []; + return null; } - - return [ - 'type' => 1, - 'components' => [[ - 'type' => 3, - 'custom_id' => "applicationSubmission-acceptTemplate-{$applicationSubmission->id}", - 'options' => $options->toArray(), - 'placeholder' => 'Accept template', - 'min_values' => 1, - 'max_values' => 1, - ]], - ]; + $row = new StringCollectorData( + custom_id: "applicationSubmission-acceptTemplate-{$applicationSubmission->id}", + options: $options, + placeholder: 'Accept template', + min_values: 1, + max_values: 1, + ); + + return new ActionRowData(components: collect([$row])); } - /** - * @return array{ - * type?: int, - * components?: array, - * placeholder: string, - * min_values: int, - * max_values: int, - * }> - * } - */ - private function getDenyActionRow(ApplicationSubmission $applicationSubmission): array + private function getDenyActionRow(ApplicationSubmission $applicationSubmission): ?ActionRowData { if ($applicationSubmission->state !== ApplicationSubmissionState::Pending) { - return []; + return null; } - $options = $applicationSubmission->application?->deniedResponses()->limit(25)->get()->map(fn ($response) => [ - 'label' => $response->name, - 'value' => "{$response->id}", - 'description' => Str::limit($response->response, 90), - ]) ?? collect(); + + /** @var Collection $options */ + $options = StringCollectorOptionData::collect($applicationSubmission->application?->deniedResponses()->limit(25)->get() ?? []); if ($options->isEmpty()) { - return []; + return null; } - - return [ - 'type' => 1, - 'components' => [[ - 'type' => 3, - 'custom_id' => "applicationSubmission-denyTemplate-{$applicationSubmission->id}", - 'options' => $options->toArray(), - 'placeholder' => 'Deny templates', - 'min_values' => 1, - 'max_values' => 1, - ]], - ]; + $row = new StringCollectorData( + custom_id: "applicationSubmission-denyTemplate-{$applicationSubmission->id}", + options: $options, + placeholder: 'Deny template', + min_values: 1, + max_values: 1, + ); + + return new ActionRowData(components: collect([$row])); } } diff --git a/app/Repositories/TicketPanelRepository.php b/app/Repositories/TicketPanelRepository.php index e53fedc..b69075a 100644 --- a/app/Repositories/TicketPanelRepository.php +++ b/app/Repositories/TicketPanelRepository.php @@ -2,6 +2,10 @@ namespace App\Repositories; +use App\Data\Discord\Component\ActionRowData; +use App\Data\Discord\Component\ButtonData; +use App\Data\Discord\Component\EmojiData; +use App\Data\Discord\Embed\EmbedData; use App\Models\TicketPanel; use Illuminate\Support\Facades\Http; @@ -13,43 +17,26 @@ public function sendPanel(TicketPanel $ticketPanel): bool if ($buttons->isEmpty()) { return false; } - /** - * @var mixed $components - */ - $components = $buttons->map(function ($ticketButton): array { - $emoji = ['name' => $ticketButton->emoji]; - if (str_contains($ticketButton->emoji, '<') && str_contains($ticketButton->emoji, '>')) { - $discordEmoji = str_replace('<', '', $ticketButton->emoji); - $discordEmoji = str_replace('>', '', $discordEmoji); - [$emojiName, $emojiId] = explode(':', $discordEmoji); - $emoji = [ - 'name' => $emojiName, - 'id' => $emojiId, - ]; - } - return [ - 'type' => 2, // button - 'custom_id' => 'ticket-create-'.$ticketButton->id, - 'style' => $ticketButton->color->value, - 'label' => $ticketButton->text, - 'emoji' => $emoji, - ]; + $components = $buttons->map(function ($ticketButton): ButtonData { + return new ButtonData( + custom_id: 'ticket-create-'.$ticketButton->id, + style: $ticketButton->color, + label: $ticketButton->text, + emoji: EmojiData::from($ticketButton), + ); }); $data = [ 'embeds' => [ - [ - 'title' => $ticketPanel->title, - 'description' => $ticketPanel->message, - 'color' => hexdec(str_replace('#', '', $ticketPanel->embed_color)), - ], + new EmbedData( + title: $ticketPanel->title, + description: $ticketPanel->message, + color: (string) hexdec(str_replace('#', '', $ticketPanel->embed_color)), + ), ], 'components' => [ - [ - 'type' => 1, - 'components' => $components, - ], + new ActionRowData(components: $components), ], ]; diff --git a/app/Repositories/TicketRepository.php b/app/Repositories/TicketRepository.php index e1a9768..3cb0b16 100644 --- a/app/Repositories/TicketRepository.php +++ b/app/Repositories/TicketRepository.php @@ -2,8 +2,12 @@ namespace App\Repositories; +use App\Data\Discord\Component\ActionRowData; +use App\Data\Discord\Component\ButtonData; +use App\Data\Discord\Component\EmojiData; +use App\Data\Discord\Embed\EmbedData; +use App\Data\Discord\Embed\FieldsData; use App\Data\Requests\CreateTicketRequest; -use App\Enums\DiscordButton; use App\Enums\TicketState; use App\Models\Ticket; use App\Models\TicketButton; @@ -116,34 +120,28 @@ public function pingRoles(Ticket $ticket): bool */ public function sendInitialMessage(Ticket $ticket): array { - $closeButton = [ - 'type' => 2, // button - 'custom_id' => 'ticket-close-'.$ticket->id, - 'style' => DiscordButton::Danger, - 'label' => 'Close', - 'emoji' => ['name' => '🔒'], - ]; - - $closeWithReasonButton = [ - 'type' => 2, // button - 'custom_id' => 'ticket-closeWithReason-'.$ticket->id, - 'style' => DiscordButton::Danger, - 'label' => 'Close With Reason', - 'emoji' => ['name' => '🔒'], - ]; + $buttons = collect([ + ButtonData::danger( + 'ticket-close-'.$ticket->id, + 'Close', + new EmojiData('🔒'), + ), + ButtonData::danger( + 'ticket-closeWithReason-'.$ticket->id, + 'Close With Reason', + new EmojiData('🔒'), + ), + ]); $response = Http::discordBot()->post('/channels/'.$ticket->channel_id.'/messages', [ 'embeds' => [ - [ - 'description' => $ticket->ticketButton?->initial_message, - 'color' => hexdec('22e629'), // Green - ], + new EmbedData( + description: $ticket->ticketButton?->initial_message, + color: (string) hexdec('22e629'), // Green + ), ], 'components' => [ - [ - 'type' => 1, - 'components' => [$closeButton, $closeWithReasonButton], - ], + new ActionRowData(components: $buttons), ], ]); @@ -158,60 +156,57 @@ public function sendTranscript(Ticket $ticket): bool */ $ticketConfig = TicketConfig::where('guild_id', $guildId)->first(); - $transcriptButton = [ - 'type' => 2, // button - 'style' => DiscordButton::Link, - 'label' => 'Transcript', - 'url' => config('services.frontend.base_url').'/ticket/transcript/'.$ticket->id, - ]; - - $embed = [ - 'title' => 'Ticket Closes', - 'color' => hexdec('22e629'), // Green - 'fields' => [ - [ - 'name' => 'Ticket ID', - 'value' => $ticket->id, - 'inline' => true, - ], - [ - 'name' => 'Opened By', - 'value' => '<@'.$ticket->created_by_discord_user_id.'>', - 'inline' => true, - ], - [ - 'name' => 'Closed By', - 'value' => '<@'.$ticket->closed_by_discord_user_id.'>', - 'inline' => true, - ], - [ - 'name' => 'Ticket type', - 'value' => $ticket->ticketButton->text ?? '---', - 'inline' => true, - ], - [ - 'name' => 'Open Time', - 'value' => 'created_at?->timestamp.'>', - 'inline' => true, - ], - [ - 'name' => 'Close Time', - 'value' => 'updated_at?->timestamp.'>', - 'inline' => true, - ], - [ - 'name' => 'Reason', - 'value' => $ticket->closed_reason ?? '---', - ], - ], - ]; + $buttons = collect([ + ButtonData::link( + 'Transcript', + config('services.frontend.base_url').'/ticket/transcript/'.$ticket->id, + ), + ]); + + $embed = new EmbedData( + title: 'Ticket Closes', + color: (string) hexdec('22e629'), // Green + fields: collect([ + new FieldsData( + name: 'Ticket ID', + value: (string) $ticket->id, + inline: true, + ), + new FieldsData( + name: 'Opened By', + value: '<@'.$ticket->created_by_discord_user_id.'>', + inline: true, + ), + new FieldsData( + name: 'Closed By', + value: '<@'.$ticket->closed_by_discord_user_id.'>', + inline: true, + ), + new FieldsData( + name: 'Ticket type', + value: $ticket->ticketButton->text ?? '---', + inline: true, + ), + new FieldsData( + name: 'Open Time', + value: 'created_at?->timestamp.'>', + inline: true, + ), + new FieldsData( + name: 'Close Time', + value: 'updated_at?->timestamp.'>', + inline: true, + ), + new FieldsData( + name: 'Reason', + value: $ticket->closed_reason ?? '---', + ), + ]), + ); $response = Http::discordBot()->post('/channels/'.$ticketConfig->transcript_channel_id.'/messages', [ - 'embeds' => [$embed], + 'embeds' => collect([$embed]), 'components' => [ - [ - 'type' => 1, - 'components' => [$transcriptButton], - ], + new ActionRowData(components: $buttons), ], ]); diff --git a/dev.kdl b/dev.kdl index 186fdab..79fabd7 100644 --- a/dev.kdl +++ b/dev.kdl @@ -1,19 +1,50 @@ layout { - pane split_direction="Vertical" { - pane split_direction="Horizontal" { - pane command="docker" name="docker startup" { + default_tab_template { + pane size=1 borderless=true { + plugin location="zellij:tab-bar" + } + children + pane size=2 borderless=true { + plugin location="zellij:status-bar" + } + } + tab name="Dump Server" { + pane { + command "php" + name "Dump Server" + args "artisan" "dump" + } + } + tab name="Laravel" { + pane split_direction="Vertical" { + pane { + command "docker" + name "docker startup" args "compose" "up" "-d" } - pane command="php" name="artisan serve" { + pane { + command "php" + name "artisan serve" args "artisan" "serve" } } - pane split_direction="Horizontal" { - pane command="php" name="dump server" { - args "artisan" "dump" - } + } + tab name="Helper" { + pane { + command "yarn" + name "yarn dev" + args "dev" + cwd "../helper" + } + } + tab name="Bot" { + pane { + command "npm" + name "npm start" + args "start" + cwd "../bot" } } } -session_name "OrdinaryApi" +session_name "Ordinary SMP" attach_to_session true diff --git a/justfile b/justfile index 0e710a7..e9c2ce5 100644 --- a/justfile +++ b/justfile @@ -3,8 +3,15 @@ dev: check: ./vendor/bin/pint + ./vendor/bin/phpstan analyse --memory-limit 2G ide: php artisan ide-helper:generate php artisan ide-helper:eloquent php artisan ide-helper:models -W + +types: + php artisan typescript:transform + +alias c := check +alias t := types