validate([ 'unread_only' => ['nullable', 'boolean'], 'per_page' => ['nullable', 'integer', 'min:1', 'max:100'], ]); $perPage = (int) ($data['per_page'] ?? 25); $unreadOnly = filter_var($data['unread_only'] ?? false, FILTER_VALIDATE_BOOL); $user = $request->user(); $query = $unreadOnly ? $user->unreadNotifications() : $user->notifications(); $page = $query->paginate($perPage); $items = $page->getCollection()->map(fn ($n) => [ 'id' => $n->id, 'type' => class_basename($n->type), 'data' => $n->data, 'read_at' => $n->read_at?->toIso8601String(), 'created_at' => $n->created_at?->toIso8601String(), ])->all(); return $this->ok($items, null, [ 'page' => $page->currentPage(), 'per_page' => $page->perPage(), 'total' => $page->total(), 'last_page' => $page->lastPage(), 'unread_count' => $user->unreadNotifications()->count(), ]); } public function markRead(Request $request, string $id): JsonResponse { $notification = $request->user()->notifications()->where('id', $id)->first(); if (! $notification) { return $this->notFound('Notification not found'); } $notification->markAsRead(); return $this->ok(['read_at' => $notification->read_at->toIso8601String()]); } public function markAllRead(Request $request): JsonResponse { $count = $request->user()->unreadNotifications()->count(); $request->user()->unreadNotifications->markAsRead(); return $this->ok(['marked_read' => $count], "Marked {$count} as read"); } public function unreadCount(Request $request): JsonResponse { return $this->ok([ 'unread_count' => $request->user()->unreadNotifications()->count(), ]); } }