filters['startDate'] ?? null; $endDate = $this->filters['endDate'] ?? null; $issueTable = (new IssueManagement)->getTable(); $departmentTable = (new Department)->getTable(); $pivotTable = 'department_issue_management'; // Get Top 10 Departments by total issues $topDepartments = Department::query() ->join($pivotTable, "{$departmentTable}.id", '=', "{$pivotTable}.department_id") ->join($issueTable, "{$pivotTable}.issue_management_id", '=', "{$issueTable}.id") ->when($startDate, fn ($q) => $q->whereDate("{$issueTable}.created_at", '>=', $startDate)) ->when($endDate, fn ($q) => $q->whereDate("{$issueTable}.created_at", '<=', $endDate)) ->select("{$departmentTable}.id", "{$departmentTable}.name", DB::raw('count(*) as total')) ->groupBy("{$departmentTable}.id", "{$departmentTable}.name") ->orderByDesc('total') ->limit(10) ->get(); if ($topDepartments->isEmpty()) { return [ 'datasets' => [], 'labels' => [], ]; } $labels = $topDepartments->pluck('name')->toArray(); $departmentIds = $topDepartments->pluck('id')->toArray(); // Get counts per sentiment for these departments $rawCounts = IssueManagement::query() ->join($pivotTable, "{$issueTable}.id", '=', "{$pivotTable}.issue_management_id") ->whereIn("{$pivotTable}.department_id", $departmentIds) ->when($startDate, fn ($q) => $q->whereDate("{$issueTable}.created_at", '>=', $startDate)) ->when($endDate, fn ($q) => $q->whereDate("{$issueTable}.created_at", '<=', $endDate)) ->select("{$pivotTable}.department_id", 'issue', DB::raw('count(*) as total')) ->groupBy("{$pivotTable}.department_id", 'issue') ->get(); $datasets = []; $sentiments = IssueSentiment::cases(); foreach ($sentiments as $sentiment) { $data = []; foreach ($departmentIds as $id) { $count = $rawCounts->where('department_id', $id) ->where('issue', $sentiment->value) ->first(); $data[] = $count ? $count->total : 0; } $datasets[] = [ 'label' => $sentiment->getLabel(), 'data' => $data, 'backgroundColor' => $this->getHexColor($sentiment), ]; } return [ 'datasets' => $datasets, 'labels' => $labels, ]; } private function getHexColor(IssueSentiment $sentiment): string { return match ($sentiment) { IssueSentiment::POSITIVE => '#10B981', // green-500 IssueSentiment::NEGATIVE => '#EF4444', // red-500 IssueSentiment::NEUTRAL => '#6B7280', // gray-500 IssueSentiment::CRISIS => '#F97316', // orange-500 }; } protected function getType(): string { return 'bar'; } protected function getOptions(): array { return [ 'plugins' => [ 'legend' => [ 'display' => true, ], ], 'scales' => [ 'x' => [ 'stacked' => true, ], 'y' => [ 'stacked' => true, ], ], ]; } }