null, 'model' => null, 'suite' => null, ]; public function resetFilters(): void { $this->filters = ['search' => null, 'model' => null, 'suite' => null]; $this->resetPage(); } #[Computed] public function sessions() { $ttl = (int) config('festbench.home_cache_ttl', 300); $user = auth()->user(); // Guest views are shared-cacheable; logged-in views may contain the // user's private bands, so they get a user-scoped key. $cacheKey = 'summary:'.($user?->id ?? 'guest').':'.md5(json_encode([$this->filters, $this->getPage()])); return Cache::remember($cacheKey, $ttl, function () use ($user) { $bands = $this->bandQuery($user)->paginate(10); $runIds = $bands->getCollection()->map(fn ($b) => $b->id)->all(); $suiteRows = $runIds === [] ? collect() : \Illuminate\Support\Facades\DB::table('session_suite_rows') ->whereIn('session_summary_id', $runIds) ->orderBy('sequence') ->get() ->groupBy('session_summary_id'); $bands->getCollection()->transform(fn ($band) => (object) [ 'band' => $band, 'suites' => $suiteRows->get($band->id, collect()), ]); return $bands; }); } private function bandQuery($user) { return \Illuminate\Support\Facades\DB::table('session_summaries') ->where(function ($q) use ($user) { $q->where('visibility', 'public'); if ($user !== null) { $q->orWhere(function ($own) use ($user) { $own->where('visibility', 'private')->where('user_id', $user->id); }); } }) ->when($this->filters['search'], fn ($q, $search) => $q->where(function ($q) use ($search) { $q->where('label', 'like', "%{$search}%") ->orWhere('model_id', 'like', "%{$search}%") ->orWhere('gpu', 'like', "%{$search}%") ->orWhere('runner_name', 'like', "%{$search}%"); })) ->when($this->filters['model'], fn ($q, $model) => $q->where('model_id', $model)) // Suite filter: keep bands containing the chosen suite ->when($this->filters['suite'], fn ($q, $suite) => $q->whereExists(function ($sub) use ($suite) { $sub->select(\Illuminate\Support\Facades\DB::raw(1)) ->from('session_suite_rows') ->whereColumn('session_suite_rows.session_summary_id', 'session_summaries.id') ->where('session_suite_rows.suite', $suite); })) ->orderByDesc('ran_at') ->orderBy('sequence'); } #[Computed] public function models(): array { return Cache::remember('summary:models', 300, function () { return \Illuminate\Support\Facades\DB::table('session_summaries') ->where('visibility', 'public') ->distinct()->orderBy('model_id')->pluck('model_id')->all(); }); } #[Computed] public function suites(): array { return Cache::remember('summary:suites', 300, function () { return \Illuminate\Support\Facades\DB::table('session_suite_rows') ->join('session_summaries', 'session_summaries.id', '=', 'session_suite_rows.session_summary_id') ->where('session_summaries.visibility', 'public') ->distinct()->orderBy('suite')->pluck('suite')->all(); }); } }; ?>
{{ __('FestBench - Benchmarks') }} {{ __('GPU, model, suite scores — click a suite line for per-task detail.') }}
{{ __('All task rows') }}
{{ __('All models') }} @foreach ($this->models as $model) {{ $model }} @endforeach {{ __('All suites') }} @foreach ($this->suites as $suite) {{ $suite }} @endforeach {{ __('Clear') }}
@if ($this->sessions->count() > 0)
@foreach ($this->sessions as $session)
{{ $session->band->gpu ?? 'unknown GPU' }} @if ($session->band->gpu_count) ×{{ $session->band->gpu_count }} @endif {{ $session->band->model_id ?? 'unknown model' }} @if ($session->band->label) {{ $session->band->label }} @else @if ($session->band->model_quant) {{ $session->band->model_quant }} @endif @if ($session->band->engine) {{ $session->band->engine }} @endif @if ($session->band->config_name) {{ $session->band->config_name }} @endif @endif {{ $session->band->runner_name ?? 'anonymous' }} {{ optional($session->band->ran_at)->format('M j Y') }}
{{-- Band total: geometric-mean tok/s across all observations + total tokens --}} @if ($session->band->total_tps !== null)
{{ __('Band total') }} {{ number_format($session->band->total_tps, 1) }} {{ __('tok/s (geo)') }} {{ number_format($session->band->total_tokens) }} {{ __('tokens') }} ✔ {{ $session->band->total_passed }} ✘ {{ $session->band->total_failed }}
@endif {{-- Column titles aligned over the suite rows (md+ only) --}}
@foreach ($session->suites as $row) @php $detailUrl = $row->suite === 'scenariobench' ? route('sessions.scenarios', $session->band->id) : route('runs.show', $row->run_id) . ($row->level && $row->suite === 'depthsweep' ? '?level=' . $row->level : ''); @endphp {{ $row->suite }} @if ($row->level) {{ $row->level }} @endif ✔ {{ $row->passed }} ✘ {{ $row->failed }} @if ($row->weighted_user_tps !== null) {{ number_format($row->weighted_user_tps, 1) }} @elseif ($row->gen_tps !== null) {{ number_format($row->gen_tps, 1) }} {{ __('gen') }} @endif {{ number_format($row->total_tokens) }} {{ __('per-task detail') }} → @endforeach
@endforeach
{{ $this->sessions->links() }}
@else
{{ __('No sessions') }} {{ __('No benchmark sessions match the current filters.') }}
@endif