14-04-2026
This commit is contained in:
parent
f58c709945
commit
0f82fea88a
72 changed files with 7414 additions and 148 deletions
125
app/Console/Commands/CheckPaymentUptime.php
Normal file
125
app/Console/Commands/CheckPaymentUptime.php
Normal file
|
|
@ -0,0 +1,125 @@
|
|||
<?php
|
||||
|
||||
namespace App\Console\Commands;
|
||||
|
||||
use App\Models\IncidentActivity;
|
||||
use App\Models\PaymentIncident;
|
||||
use App\Models\ProviderUptimeLog;
|
||||
use Illuminate\Console\Command;
|
||||
use Illuminate\Support\Facades\Http;
|
||||
use Illuminate\Support\Facades\Log;
|
||||
|
||||
class CheckPaymentUptime extends Command
|
||||
{
|
||||
protected $signature = 'payment:check-uptime';
|
||||
|
||||
protected $description = 'Prüft die Erreichbarkeit von PAYONE und legt bei Ausfall automatisch einen Incident an.';
|
||||
|
||||
/**
|
||||
* @var array<string, string>
|
||||
*/
|
||||
private array $endpoints = [
|
||||
'payone' => 'https://api.pay1.de/post-gateway/',
|
||||
];
|
||||
|
||||
public function handle(): int
|
||||
{
|
||||
Log::channel('payment')->info('COMMAND [payment:check-uptime] started.');
|
||||
|
||||
foreach ($this->endpoints as $provider => $url) {
|
||||
$this->checkProvider($provider, $url);
|
||||
}
|
||||
|
||||
Log::channel('payment')->info('COMMAND [payment:check-uptime] finished.');
|
||||
|
||||
return self::SUCCESS;
|
||||
}
|
||||
|
||||
private function checkProvider(string $provider, string $url): void
|
||||
{
|
||||
$startMs = now()->valueOf();
|
||||
|
||||
try {
|
||||
$response = Http::timeout(10)->head($url);
|
||||
$responseTimeMs = now()->valueOf() - $startMs;
|
||||
$isUp = $response->successful() || $response->status() < 500;
|
||||
$errorMessage = $isUp ? null : 'HTTP '.$response->status();
|
||||
} catch (\Exception $e) {
|
||||
$responseTimeMs = now()->valueOf() - $startMs;
|
||||
$isUp = false;
|
||||
$errorMessage = $e->getMessage();
|
||||
}
|
||||
|
||||
ProviderUptimeLog::create([
|
||||
'provider' => $provider,
|
||||
'is_up' => $isUp,
|
||||
'response_time_ms' => (int) $responseTimeMs,
|
||||
'error_message' => $errorMessage,
|
||||
'checked_at' => now(),
|
||||
]);
|
||||
|
||||
$status = $isUp ? 'UP' : 'DOWN';
|
||||
$this->line("[{$provider}] {$status} ({$responseTimeMs}ms)");
|
||||
Log::channel('payment')->info("[payment:check-uptime] {$provider} {$status}", [
|
||||
'response_time_ms' => $responseTimeMs,
|
||||
'error_message' => $errorMessage,
|
||||
]);
|
||||
|
||||
if (! $isUp) {
|
||||
$this->handleOutage($provider, $errorMessage);
|
||||
} else {
|
||||
$this->handleRecovery($provider);
|
||||
}
|
||||
}
|
||||
|
||||
private function handleOutage(string $provider, ?string $errorMessage): void
|
||||
{
|
||||
$incident = PaymentIncident::firstOrCreate(
|
||||
[
|
||||
'provider' => $provider,
|
||||
'type' => 'outage',
|
||||
'status' => 'open',
|
||||
],
|
||||
[
|
||||
'title' => 'Automatisch: '.strtoupper($provider).' nicht erreichbar',
|
||||
'description' => 'Uptime-Check hat einen Ausfall erkannt.',
|
||||
'severity' => 'critical',
|
||||
'detected_at' => now()->startOfHour(),
|
||||
]
|
||||
);
|
||||
|
||||
IncidentActivity::create([
|
||||
'incident_id' => $incident->id,
|
||||
'type' => 'note',
|
||||
'title' => 'Uptime-Check: '.strtoupper($provider).' DOWN',
|
||||
'content' => $errorMessage,
|
||||
'author' => 'System',
|
||||
]);
|
||||
|
||||
Log::channel('payment')->error("[payment:check-uptime] Outage-Incident #{$incident->id} für {$provider}.");
|
||||
}
|
||||
|
||||
private function handleRecovery(string $provider): void
|
||||
{
|
||||
$openOutages = PaymentIncident::where('provider', $provider)
|
||||
->where('type', 'outage')
|
||||
->whereIn('status', ['open', 'in_progress'])
|
||||
->get();
|
||||
|
||||
foreach ($openOutages as $incident) {
|
||||
$incident->update([
|
||||
'status' => 'resolved',
|
||||
'resolved_at' => now(),
|
||||
]);
|
||||
|
||||
IncidentActivity::create([
|
||||
'incident_id' => $incident->id,
|
||||
'type' => 'status_change',
|
||||
'title' => 'Automatisch aufgelöst: '.strtoupper($provider).' ist wieder erreichbar',
|
||||
'author' => 'System',
|
||||
]);
|
||||
|
||||
Log::channel('payment')->info("[payment:check-uptime] Incident #{$incident->id} für {$provider} automatisch aufgelöst.");
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
@ -5,6 +5,7 @@ namespace App\Console;
|
|||
use App\Console\Commands\BusinessStore;
|
||||
use App\Console\Commands\BusinessStoreOptimized;
|
||||
use App\Console\Commands\CheckPaymentsAccount;
|
||||
use App\Console\Commands\CheckPaymentUptime;
|
||||
use App\Console\Commands\DhlUpdateTracking;
|
||||
use App\Console\Commands\UserCleanup;
|
||||
use App\Console\Commands\UserMakeAboOrder;
|
||||
|
|
@ -21,6 +22,7 @@ class Kernel extends ConsoleKernel
|
|||
protected $commands = [
|
||||
BusinessStore::class,
|
||||
BusinessStoreOptimized::class,
|
||||
CheckPaymentUptime::class,
|
||||
CheckPaymentsAccount::class,
|
||||
UserMakeAboOrder::class,
|
||||
UserCleanup::class,
|
||||
|
|
@ -34,6 +36,12 @@ class Kernel extends ConsoleKernel
|
|||
*/
|
||||
protected function schedule(Schedule $schedule)
|
||||
{
|
||||
// Uptime-Check: PAYONE-Erreichbarkeit alle 5 Minuten prüfen
|
||||
$schedule->command('payment:check-uptime')
|
||||
->everyFiveMinutes()
|
||||
->withoutOverlapping()
|
||||
->runInBackground();
|
||||
|
||||
// Job 1: Überprüft täglich um 02:00 Uhr die Zahlungskonten.
|
||||
$schedule->command('payments:check-accounts')->dailyAt('02:00');
|
||||
// Jobs 2, 3, 4: Die Befehle aus deinem alten Shell-Skript.
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue