map(function ($category) { return [ 'id' => $category->id, 'name' => $category->name, ]; }); return $this->success($categories, 'Success', 'Categories List'); } public function index(Request $request) { $request->validate([ 'category_id' => 'nullable|exists:legal_opinion_categories,id', 'sort' => 'nullable|in:asc,desc', 'per_page' => 'nullable|integer|min:1|max:100', ]); $query = LegalOpinion::query(); if ($request->filled('category_id')) { $query->where('category_id', $request->category_id); } $sortOrder = $request->input('sort', 'desc'); $query->orderBy('opinion_date', $sortOrder); $perPage = min(max((int) $request->input('per_page', 15), 10), 100); $paginator = $query->paginate($perPage); $items = collect($paginator->items())->map(function ($item) { return $this->formatItem($item); }); $responseData = [ 'items' => $items, 'current_page' => $paginator->currentPage(), 'last_page' => $paginator->lastPage(), 'per_page' => $paginator->perPage(), 'total' => $paginator->total(), ]; return $this->success($responseData, 'Success', 'Legal Opinions Fetched'); } public function search(Request $request) { $request->validate([ 'search' => 'nullable|string', 'per_page' => 'nullable|integer|min:1|max:100', ]); $query = LegalOpinion::query(); if ($request->filled('search')) { $searchTerm = $request->input('search'); $query->where(function ($q) use ($searchTerm) { $q->where('opinion_number', 'LIKE', "%{$searchTerm}%") ->orWhere('subject', 'LIKE', "%{$searchTerm}%") ->orWhere('full_text', 'LIKE', "%{$searchTerm}%") ->orWhere('issuing_authority', 'LIKE', "%{$searchTerm}%"); }); } $perPage = min(max((int) $request->input('per_page', 15), 10), 100); $paginator = $query->orderBy('opinion_date', 'desc')->paginate($perPage); $items = collect($paginator->items())->map(function ($item) { return $this->formatItem($item); }); $responseData = [ 'items' => $items, 'current_page' => $paginator->currentPage(), 'last_page' => $paginator->lastPage(), 'per_page' => $paginator->perPage(), 'total' => $paginator->total(), ]; return $this->success($responseData, 'Success', 'Search Results Fetched'); } public function fast_search(Request $request) { $searchTerm = $request->input('search'); $query = LegalOpinion::query(); if ($request->filled('search')) { $query->where(function ($q) use ($searchTerm) { $q->where('opinion_number', 'LIKE', "%{$searchTerm}%") ->orWhere('subject', 'LIKE', "%{$searchTerm}%") ->orWhere('full_text', 'LIKE', "%{$searchTerm}%") ->orWhere('issuing_authority', 'LIKE', "%{$searchTerm}%"); }); } $count = $query->count(); // Limit to 5 results for fast search dropdown $items = $query->orderBy('opinion_date', 'desc')->take(5)->get()->map(function ($item) { return $this->formatItem($item); }); return $this->success([ 'items' => $items, 'count' => $count ], 'Success', 'Fast Search Results'); } public function pager($id) { $current = LegalOpinion::find($id); if (!$current) { return $this->failed([], [ 'title' => 'خطا', 'message' => 'نظریه قانونی مورد نظر یافت نشد.' ], 404); } $previousItem = LegalOpinion::where(function ($query) use ($current) { if ($current->opinion_date) { $query->where('opinion_date', '<', $current->opinion_date) ->orWhere(function ($subQuery) use ($current) { $subQuery->where('opinion_date', '=', $current->opinion_date) ->where('id', '<', $current->id); }); } else { $query->whereNull('opinion_date')->where('id', '<', $current->id); } }) ->orderBy('opinion_date', 'desc') ->orderBy('id', 'desc') ->first(); $nextItem = LegalOpinion::where(function ($query) use ($current) { if ($current->opinion_date) { $query->where('opinion_date', '>', $current->opinion_date) ->orWhere(function ($subQuery) use ($current) { $subQuery->where('opinion_date', '=', $current->opinion_date) ->where('id', '>', $current->id); }); } else { $query->whereNotNull('opinion_date') ->orWhere(function ($subQuery) use ($current) { $subQuery->whereNull('opinion_date')->where('id', '>', $current->id); }); } }) ->orderBy('opinion_date', 'asc') ->orderBy('id', 'asc') ->first(); $results = array_values(array_filter([ $previousItem ? $this->formatItem($previousItem) : null, $this->formatItem($current), $nextItem ? $this->formatItem($nextItem) : null ])); return $this->success($results, 'Success', 'Pager Window Details'); } private function isLockedForCurrentUser($item): bool { return ! auth()->user()->isSubscriber() && (bool) ($item->is_locked ?? false); } private function formatItem($item) { $isLocked = $this->isLockedForCurrentUser($item); return [ 'id' => $item->id, 'opinion_number' => $item->opinion_number, 'opinion_date' => $item->opinion_date, 'subject' => $item->subject, 'full_text' => $isLocked ? null : $item->full_text, 'issuing_authority' => $item->issuing_authority, 'category_id' => $item->category_id, 'category_name' => optional($item->category)->name, 'is_locked' => $isLocked, ]; } }