diff --git a/IMPLEMENTATION_DETAILS.md b/IMPLEMENTATION_DETAILS.md new file mode 100644 index 00000000000..1c26266a759 --- /dev/null +++ b/IMPLEMENTATION_DETAILS.md @@ -0,0 +1,239 @@ +# Sticky Incidents Fix - Code Changes Summary + +## Overview +This document provides a detailed breakdown of the code changes made to fix the sticky incidents display issue. + +## Problem Statement +From the GitHub issue: +- User created an incident and marked it as "sticky" +- Expected: Incident should display prominently at the top of the status page +- Actual: Incident only appeared in the "Past Incidents" section under its date (1/2/2026) + +## Solution Architecture + +### 1. Data Layer Changes (`IncidentTimeline.php`) + +#### New Method: `stickiedIncidents()` +Fetches all sticky incidents that should be displayed at the top: + +```php +private function stickiedIncidents(): Collection +{ + return Incident::query() + ->with([ + 'components', + 'updates' => fn ($query) => $query->orderByDesc('created_at'), + ]) + ->visible(auth()->check()) + ->stickied() // Uses existing scope from Incident model + ->get() + ->sortByDesc(fn (Incident $incident) => $incident->timestamp); +} +``` + +**Key Points:** +- Uses the existing `stickied()` scope defined in the Incident model +- Maintains visibility checks (respects authentication status) +- Eager loads components and updates for performance +- Sorts by timestamp (newest first) + +#### Modified Method: `incidents()` +Excludes sticky incidents from the regular timeline: + +```php +private function incidents(Carbon $startDate, Carbon $endDate, bool $onlyDisruptedDays = false): Collection +{ + return Incident::query() + ->with([...]) + ->visible(auth()->check()) + ->where('stickied', false) // ← NEW: Exclude sticky incidents + ->when($this->appSettings->recent_incidents_only, function ($query) { + // ... existing logic + }) + // ... rest of the method +} +``` + +**Key Points:** +- Added `->where('stickied', false)` to explicitly exclude sticky incidents +- This ensures sticky incidents don't appear in both sections +- All other logic remains unchanged + +#### Updated Method: `render()` +Passes sticky incidents to the view: + +```php +public function render(): View +{ + // ... existing logic + + return view('cachet::components.incident-timeline', [ + 'stickiedIncidents' => $this->stickiedIncidents(), // ← NEW + 'incidents' => $this->incidents(...), + // ... existing data + ]); +} +``` + +### 2. Presentation Layer Changes (`incident-timeline.blade.php`) + +#### New Section: Stickied Incidents +Added at the top of the timeline, before "Past Incidents": + +```blade +@if($stickiedIncidents->isNotEmpty()) +