76 lines
2.2 KiB
PHP
76 lines
2.2 KiB
PHP
<?php
|
|
|
|
declare(strict_types=1);
|
|
|
|
namespace App\Filament\Widgets\Dashboard;
|
|
|
|
use App\Models\Tenant;
|
|
use App\Support\OpsUx\ActiveRuns;
|
|
use App\Support\TenantDashboard\TenantDashboardSummaryBuilder;
|
|
use Filament\Facades\Filament;
|
|
use Filament\Widgets\StatsOverviewWidget;
|
|
use Filament\Widgets\StatsOverviewWidget\Stat;
|
|
|
|
class DashboardKpis extends StatsOverviewWidget
|
|
{
|
|
protected int|string|array $columnSpan = 'full';
|
|
protected static bool $isLazy = false;
|
|
|
|
protected function getPollingInterval(): ?string
|
|
{
|
|
return ActiveRuns::pollingIntervalForTenant(Filament::getTenant());
|
|
}
|
|
|
|
/**
|
|
* @return array<Stat>
|
|
*/
|
|
protected function getStats(): array
|
|
{
|
|
$tenant = Filament::getTenant();
|
|
|
|
if (! $tenant instanceof Tenant) {
|
|
return [];
|
|
}
|
|
|
|
$summary = app(TenantDashboardSummaryBuilder::class)->build($tenant, auth()->user());
|
|
|
|
$stats = [];
|
|
|
|
foreach ($summary->kpis as $kpi) {
|
|
if (count($stats) >= 4) {
|
|
break;
|
|
}
|
|
|
|
$color = $kpi['tone'] === 'gray' ? null : $kpi['tone'];
|
|
$icon = is_string($kpi['icon'] ?? null) ? $kpi['icon'] : null;
|
|
$chart = is_array($kpi['chart'] ?? null) ? $kpi['chart'] : null;
|
|
|
|
$stat = Stat::make($kpi['label'], (string) $kpi['value'])
|
|
->description($kpi['description'])
|
|
->color($color)
|
|
->extraAttributes([
|
|
'data-testid' => 'tenant-dashboard-kpi',
|
|
'data-kpi-key' => (string) ($kpi['key'] ?? ''),
|
|
'data-kpi-has-icon' => $icon !== null ? 'true' : 'false',
|
|
'data-kpi-has-chart' => $chart !== null ? 'true' : 'false',
|
|
]);
|
|
|
|
if ($icon !== null) {
|
|
$stat->descriptionIcon($icon);
|
|
}
|
|
|
|
if ($chart !== null) {
|
|
$stat->chart(array_map(static fn (mixed $point): int => (int) $point, $chart));
|
|
}
|
|
|
|
if (!empty($kpi['actionUrl'])) {
|
|
$stat->url($kpi['actionUrl']);
|
|
}
|
|
|
|
$stats[] = $stat;
|
|
}
|
|
|
|
return $stats;
|
|
}
|
|
}
|