*/ protected function getStats(): array { $tenant = Filament::getTenant(); if (! $tenant instanceof Tenant) { return [ Stat::make('Total Runs (30 days)', 0), Stat::make('Active Runs', 0), Stat::make('Failed/Partial (7 days)', 0), Stat::make('Avg Duration (7 days)', '—'), ]; } $tenantId = (int) $tenant->getKey(); $totalRuns30Days = (int) OperationRun::query() ->where('tenant_id', $tenantId) ->where('created_at', '>=', now()->subDays(30)) ->count(); $activeRuns = (int) OperationRun::query() ->where('tenant_id', $tenantId) ->whereIn('status', [ OperationRunStatus::Queued->value, OperationRunStatus::Running->value, ]) ->count(); $failedOrPartial7Days = (int) OperationRun::query() ->where('tenant_id', $tenantId) ->where('status', OperationRunStatus::Completed->value) ->whereIn('outcome', [ OperationRunOutcome::Failed->value, OperationRunOutcome::PartiallySucceeded->value, ]) ->where('completed_at', '>=', now()->subDays(7)) ->count(); /** @var Collection $recentCompletedRuns */ $recentCompletedRuns = OperationRun::query() ->where('tenant_id', $tenantId) ->where('status', OperationRunStatus::Completed->value) ->whereNotNull('started_at') ->whereNotNull('completed_at') ->where('completed_at', '>=', now()->subDays(7)) ->latest('id') ->limit(200) ->get(['started_at', 'completed_at']); $durations = $recentCompletedRuns ->map(function (OperationRun $run): ?int { if (! $run->started_at || ! $run->completed_at) { return null; } $seconds = $run->completed_at->diffInSeconds($run->started_at); if (is_int($seconds)) { return $seconds; } return (int) round((float) $seconds); }) ->filter(fn (?int $seconds): bool => is_int($seconds) && $seconds > 0) ->values(); $avgDuration7Days = '—'; if ($durations->isNotEmpty()) { $avgDurationSeconds = (int) round($durations->avg() ?? 0); $avgDuration7Days = self::formatDurationSeconds($avgDurationSeconds); } return [ Stat::make('Total Runs (30 days)', $totalRuns30Days), Stat::make('Active Runs', $activeRuns), Stat::make('Failed/Partial (7 days)', $failedOrPartial7Days), Stat::make('Avg Duration (7 days)', $avgDuration7Days), ]; } private static function formatDurationSeconds(int $seconds): string { if ($seconds <= 0) { return '—'; } if ($seconds < 60) { return $seconds.'s'; } $interval = CarbonInterval::seconds($seconds)->cascade(); if ($seconds < 3600) { return sprintf('%dm %ds', $interval->minutes, $interval->seconds); } return sprintf('%dh %dm', $interval->hours, $interval->minutes); } }