Files
Andras Bacsai 7837a07ba2 fix(notifications): disable channels after repeated configuration failures
Count invalid keys, tokens, and deleted webhooks in a new failure_count column
on each notification settings table, like servers.unreachable_count. After 3
failures in a row the channel is disabled and the team is told by instance
email and its other channels. Rate limits and server errors are retried and
not counted; test notifications never count.
2026-10-12 14:37:58 +02:00

79 lines
3.9 KiB
PHP

<?php
namespace App\Notifications\Channels;
use App\Jobs\SendMessageToTelegramJob;
use App\Notifications\Application\DeploymentFailed;
use App\Notifications\Application\DeploymentSuccess;
use App\Notifications\Application\RestartLimitReached;
use App\Notifications\Application\StatusChanged;
use App\Notifications\Container\ContainerRestarted;
use App\Notifications\Database\BackupFailed;
use App\Notifications\Database\BackupMissing;
use App\Notifications\Database\BackupSuccess;
use App\Notifications\Database\BackupSuccessWithS3Warning;
use App\Notifications\ScheduledTask\TaskFailed;
use App\Notifications\ScheduledTask\TaskSuccess;
use App\Notifications\Server\DockerCleanupFailed;
use App\Notifications\Server\DockerCleanupSuccess;
use App\Notifications\Server\HighDiskUsage;
use App\Notifications\Server\Reachable;
use App\Notifications\Server\ServerPatchCheck;
use App\Notifications\Server\TraefikVersionOutdated;
use App\Notifications\Server\Unreachable;
use App\Notifications\VolumeBackup\BackupFailed as VolumeBackupFailed;
use App\Notifications\VolumeBackup\BackupMissing as VolumeBackupMissing;
use App\Notifications\VolumeBackup\BackupSuccess as VolumeBackupSuccess;
use App\Notifications\VolumeBackup\RecoveryFailed as VolumeBackupRecoveryFailed;
class TelegramChannel
{
public function send($notifiable, $notification): void
{
$data = $notification->toTelegram($notifiable);
$settings = $notifiable->telegramNotificationSettings;
$message = data_get($data, 'message');
$buttons = data_get($data, 'buttons', []);
$telegramToken = $settings->telegram_token;
$chatId = $settings->telegram_chat_id;
$threadId = match (get_class($notification)) {
DeploymentSuccess::class => $settings->telegram_notifications_deployment_success_thread_id,
DeploymentFailed::class => $settings->telegram_notifications_deployment_failure_thread_id,
StatusChanged::class,
ContainerRestarted::class => $settings->telegram_notifications_status_change_thread_id,
RestartLimitReached::class => $settings->telegram_notifications_restart_limit_reached_thread_id,
BackupSuccess::class => $settings->telegram_notifications_backup_success_thread_id,
VolumeBackupSuccess::class => $notification->warning
? $settings->telegram_notifications_backup_failure_thread_id
: $settings->telegram_notifications_backup_success_thread_id,
BackupFailed::class,
BackupMissing::class,
BackupSuccessWithS3Warning::class,
VolumeBackupFailed::class,
VolumeBackupMissing::class,
VolumeBackupRecoveryFailed::class => $settings->telegram_notifications_backup_failure_thread_id,
TaskSuccess::class => $settings->telegram_notifications_scheduled_task_success_thread_id,
TaskFailed::class => $settings->telegram_notifications_scheduled_task_failure_thread_id,
DockerCleanupSuccess::class => $settings->telegram_notifications_docker_cleanup_success_thread_id,
DockerCleanupFailed::class => $settings->telegram_notifications_docker_cleanup_failure_thread_id,
HighDiskUsage::class => $settings->telegram_notifications_server_disk_usage_thread_id,
Unreachable::class => $settings->telegram_notifications_server_unreachable_thread_id,
Reachable::class => $settings->telegram_notifications_server_reachable_thread_id,
ServerPatchCheck::class => $settings->telegram_notifications_server_patch_thread_id,
TraefikVersionOutdated::class => $settings->telegram_notifications_traefik_outdated_thread_id,
default => null,
};
if (! $telegramToken || ! $chatId || ! $message) {
return;
}
SendMessageToTelegramJob::dispatch($message, $buttons, $telegramToken, $chatId, $threadId, data_get($notification, 'isTestNotification', false) ? null : $settings);
}
}