authorizeAbility($request, 'queues.view'); $owner = $this->ownerRef($request); $organization = $this->organization($request); $queues = ServiceQueue::owned($owner) ->where('organization_id', $organization->id) ->with(['branch', 'department']) ->when(true, fn ($q) => $this->scopeToBranch($request, $q)) ->orderBy('name') ->paginate(20); return view('qms.queues.index', compact('queues', 'organization')); } public function show(Request $request, ServiceQueue $serviceQueue): View { $this->authorizeAbility($request, 'queues.view'); $this->authorizeOwner($request, $serviceQueue); $serviceQueue->load(['branch', 'department']); $waiting = Ticket::owned($this->ownerRef($request)) ->where('service_queue_id', $serviceQueue->id) ->where('status', 'waiting') ->count(); return view('qms.queues.show', [ 'queue' => $serviceQueue, 'waiting' => $waiting, ]); } public function create(Request $request): View { $this->authorizeAbility($request, 'queues.manage'); $owner = $this->ownerRef($request); $organization = $this->organization($request); $branches = Branch::owned($owner) ->where('organization_id', $organization->id) ->where('is_active', true) ->orderBy('name') ->get(); return view('qms.queues.create', [ 'organization' => $organization, 'branches' => $branches, 'strategies' => config('qms.queue_strategies'), ]); } public function store(Request $request): RedirectResponse { $this->authorizeAbility($request, 'queues.manage'); $owner = $this->ownerRef($request); $organization = $this->organization($request); $currentCount = ServiceQueue::owned($owner)->where('organization_id', $organization->id)->count(); if (! app(PlanService::class)->canAddQueue($organization, $currentCount)) { return back()->withInput()->with('error', 'Your plan allows '.$currentCount.' queues. Upgrade to Pro for unlimited queues.'); } $validated = $this->validatedQueue($request); abort_unless( Branch::owned($owner)->where('organization_id', $organization->id)->where('id', $validated['branch_id'])->exists(), 404, ); $queue = ServiceQueue::create([ ...$validated, 'owner_ref' => $owner, 'organization_id' => $organization->id, 'color' => $validated['color'] ?? '#4f46e5', 'avg_service_seconds' => $validated['avg_service_seconds'] ?? 300, 'is_active' => $request->boolean('is_active', true), ]); AuditLogger::record($owner, 'service_queue.created', $organization->id, $owner, ServiceQueue::class, $queue->id); return redirect()->route('qms.queues.show', $queue)->with('success', 'Queue created.'); } public function edit(Request $request, ServiceQueue $serviceQueue): View { $this->authorizeAbility($request, 'queues.manage'); $this->authorizeOwner($request, $serviceQueue); $owner = $this->ownerRef($request); return view('qms.queues.edit', [ 'queue' => $serviceQueue, 'branches' => Branch::owned($owner)->where('organization_id', $serviceQueue->organization_id)->orderBy('name')->get(), 'strategies' => config('qms.queue_strategies'), ]); } public function update(Request $request, ServiceQueue $serviceQueue): RedirectResponse { $this->authorizeAbility($request, 'queues.manage'); $this->authorizeOwner($request, $serviceQueue); $validated = $this->validatedQueue($request, updating: true); $serviceQueue->update([ ...$validated, 'color' => $validated['color'] ?? $serviceQueue->color, 'is_active' => $request->boolean('is_active', $serviceQueue->is_active), ]); AuditLogger::record($this->ownerRef($request), 'service_queue.updated', $serviceQueue->organization_id, $this->ownerRef($request), ServiceQueue::class, $serviceQueue->id); return redirect()->route('qms.queues.show', $serviceQueue)->with('success', 'Queue updated.'); } public function pause(Request $request, ServiceQueue $serviceQueue): RedirectResponse { $this->authorizeAbility($request, 'queues.manage'); $this->authorizeOwner($request, $serviceQueue); app(\App\Services\Qms\QueueEngine::class)->pauseQueue($serviceQueue, $this->ownerRef($request)); return back()->with('success', 'Queue paused.'); } public function resume(Request $request, ServiceQueue $serviceQueue): RedirectResponse { $this->authorizeAbility($request, 'queues.manage'); $this->authorizeOwner($request, $serviceQueue); app(\App\Services\Qms\QueueEngine::class)->resumeQueue($serviceQueue, $this->ownerRef($request)); return back()->with('success', 'Queue resumed.'); } /** * @return array */ protected function validatedQueue(Request $request, bool $updating = false): array { return $request->validate([ 'name' => ['required', 'string', 'max:255'], 'description' => ['nullable', 'string', 'max:1000'], 'branch_id' => ['required', 'exists:queue_branches,id'], 'department_id' => ['nullable', 'exists:queue_departments,id'], 'color' => ['nullable', 'string', 'max:20'], 'prefix' => [$updating ? 'sometimes' : 'required', 'string', 'max:10'], 'strategy' => ['required', 'string', 'in:'.implode(',', array_keys(config('qms.queue_strategies')))], 'avg_service_seconds' => ['nullable', 'integer', 'min:60', 'max:7200'], 'max_capacity' => ['nullable', 'integer', 'min:1'], 'is_active' => ['boolean'], ]); } }