fix: tenant dashboard baseline compare widget

This commit is contained in:
Ahmed Darrazi 2026-02-20 14:15:41 +01:00
parent 8f8bc24d1d
commit d75ee3614e
5 changed files with 127 additions and 5 deletions

View File

@ -4,9 +4,9 @@
namespace App\Filament\Widgets\Dashboard;
use App\Models\BaselineCompareRun;
use App\Models\BaselineTenantAssignment;
use App\Models\Finding;
use App\Models\OperationRun;
use App\Models\Tenant;
use Filament\Facades\Filament;
use Filament\Widgets\Widget;
@ -69,11 +69,12 @@ protected function getViewData(): array
->where('severity', Finding::SEVERITY_LOW)
->count();
$latestRun = BaselineCompareRun::query()
$latestRun = OperationRun::query()
->where('tenant_id', $tenant->getKey())
->where('baseline_profile_id', $profile->getKey())
->whereNotNull('finished_at')
->latest('finished_at')
->where('type', 'baseline_compare')
->where('context->baseline_profile_id', (string) $profile->getKey())
->whereNotNull('completed_at')
->latest('completed_at')
->first();
return [

View File

@ -0,0 +1,26 @@
# Implementation Plan: BaselineCompareRun model bugfix
**Branch**: `feat/700-bugfix` | **Date**: 2026-02-20 | **Spec**: `specs/feat/700-bugfix/spec.md`
## Summary
Fix runtime crash caused by a missing Eloquent model referenced by a Filament dashboard widget.
## Technical Context
- PHP 8.4.x, Laravel 12
- Filament v5, Livewire v4
- PostgreSQL (Sail locally)
- Tests: Pest v4 (`vendor/bin/sail artisan test --compact`)
## Approach
1. Identify intended storage for baseline compare runs:
- If a `baseline_compare_runs` table already exists, implement `App\Models\BaselineCompareRun` mapped to it.
- If not, align the widget to an existing persistence type (likely `OperationRun`) without changing UX.
2. Add a regression test that exercises the tenant dashboard route and asserts a successful response.
3. Run Pint on dirty files and run the focused test.
## Risks
- Introducing a new model without an existing table could still fail at runtime. Prefer minimal, compatibility-first changes.

View File

@ -0,0 +1,29 @@
# Bugfix Specification: BaselineCompareRun missing model
**Branch**: `feat/700-bugfix`
**Created**: 2026-02-20
**Status**: Ready
## Problem
Navigating to the tenant dashboard (`/admin/t/{tenant}`) throws an Internal Server Error:
- `Class "App\Models\BaselineCompareRun" not found`
The stack trace points to the dashboard widget `app/Filament/Widgets/Dashboard/BaselineCompareNow.php`.
## Goal
- Tenant dashboard loads successfully.
- Baseline compare widget can safely query baseline compare run state without a fatal error.
## Non-Goals
- No UX redesign.
- No new baseline-compare workflow features beyond restoring runtime stability.
## Acceptance Criteria
- Visiting `/admin/t/{tenant}` does not throw a 500.
- The widget renders even when there are no baseline compare runs.
- A focused automated test covers the regression.

View File

@ -0,0 +1,20 @@
---
description: "Tasks for feat/700-bugfix (BaselineCompareRun missing model)"
---
# Tasks: feat/700-bugfix
**Input**: `specs/feat/700-bugfix/spec.md` and `specs/feat/700-bugfix/plan.md`
## Setup
- [X] T001 Confirm whether baseline compare runs table exists
## Tests (TDD)
- [X] T010 Add regression test for tenant dashboard (no 500)
## Core
- [X] T020 Fix missing BaselineCompareRun reference (model or widget)
## Validation
- [X] T030 Run Pint (dirty)
- [X] T040 Run focused tests via Sail

View File

@ -0,0 +1,46 @@
<?php
declare(strict_types=1);
use App\Filament\Pages\TenantDashboard;
use App\Models\BaselineProfile;
use App\Models\BaselineTenantAssignment;
use App\Models\OperationRun;
use Illuminate\Foundation\Testing\RefreshDatabase;
uses(RefreshDatabase::class);
it('renders the tenant dashboard when a baseline assignment exists (regression: missing BaselineCompareRun model)', function (): void {
[$user, $tenant] = createUserWithTenant(role: 'owner');
$profile = BaselineProfile::factory()->create([
'workspace_id' => (int) $tenant->workspace_id,
'name' => 'Baseline A',
]);
BaselineTenantAssignment::factory()->create([
'workspace_id' => (int) $tenant->workspace_id,
'tenant_id' => (int) $tenant->getKey(),
'baseline_profile_id' => (int) $profile->getKey(),
]);
OperationRun::factory()->create([
'tenant_id' => (int) $tenant->getKey(),
'workspace_id' => (int) $tenant->workspace_id,
'type' => 'baseline_compare',
'status' => 'completed',
'outcome' => 'succeeded',
'initiator_name' => 'System',
'context' => [
'baseline_profile_id' => (int) $profile->getKey(),
],
'completed_at' => now()->subDay(),
]);
$this->actingAs($user)
->get(TenantDashboard::getUrl(tenant: $tenant))
->assertOk()
->assertSee('Baseline Governance')
->assertSee('Baseline A')
->assertSee('No open drift — baseline compliant');
});