fixe duploads and attachments now with colors tab and enhancements

This commit is contained in:
Mark Gregory
2026-06-16 19:08:23 +01:00
parent f8ae45d810
commit 30471e542c
2 changed files with 52 additions and 22 deletions
+37 -7
View File
@@ -41,11 +41,11 @@ final class TicketShow extends Component
/** @var array<int, TemporaryUploadedFile> */
public array $attachments = [];
public ?int $status_id = null;
public int|string|null $status_id = null;
public ?int $priority_id = null;
public int|string|null $priority_id = null;
public ?int $agent_id = null;
public int|string|null $agent_id = null;
public ?int $reply_parent_id = null;
@@ -225,10 +225,7 @@ final class TicketShow extends Component
$agentId = $this->normaliseNullableInt($this->agent_id);
validator(
['agent_id' => $agentId],
['agent_id' => ['nullable', 'integer', Rule::exists('users', 'id')]],
)->validate();
$this->validateAssignableAgent($agentId);
abort_unless(Schema::hasColumn('helpdesk_tickets', 'agent_id'), 500, 'The helpdesk_tickets.agent_id column is missing.');
@@ -310,6 +307,39 @@ final class TicketShow extends Component
return $ticket;
}
/**
* Validate that the selected agent exists and belongs to this ticket's company context.
*/
private function validateAssignableAgent(?int $agentId): void
{
if ($agentId === null) {
return;
}
$rule = Rule::exists('users', 'id');
if ($this->ticket->company_id !== null && Schema::hasColumn('users', 'company_id')) {
$ticketCompanyId = (int) $this->ticket->company_id;
$currentAgentId = $this->ticket->agent_id === null ? null : (int) $this->ticket->agent_id;
$rule->where(function ($query) use ($ticketCompanyId, $currentAgentId): void {
$query->where(function ($tenantQuery) use ($ticketCompanyId): void {
$tenantQuery->where('company_id', $ticketCompanyId)
->orWhereNull('company_id');
});
if ($currentAgentId !== null) {
$query->orWhere('id', $currentAgentId);
}
});
}
validator(
['agent_id' => $agentId],
['agent_id' => ['nullable', 'integer', $rule]],
)->validate();
}
/**
* Return assignable users for this ticket.
*
@@ -202,10 +202,10 @@
@can('update', $ticket)
<div class="rounded-2xl border border-zinc-200 bg-white p-5 shadow-sm dark:border-zinc-700 dark:bg-zinc-900">
<div class="mb-5 rounded-2xl bg-gradient-to-r from-blue-700 via-indigo-700 to-violet-700 px-4 py-4 text-white shadow-sm">
<div class="mb-4 rounded-2xl bg-gradient-to-r from-blue-700 via-indigo-700 to-violet-700 px-4 py-3 text-white shadow-sm">
<p class="text-xs font-black uppercase tracking-[0.24em] text-blue-100">Ticket controls</p>
<h2 class="mt-1 text-lg font-black tracking-tight">Assignment, status and priority</h2>
<p class="mt-1 text-sm font-semibold text-blue-100/90">Use the explicit update buttons below to save each change.</p>
<h2 class="mt-1 text-base font-black tracking-tight">Assignment, status and priority</h2>
<p class="mt-1 text-xs font-semibold text-blue-100/90">Choose a value, then save the specific change.</p>
</div>
@if (session('ticket-action-updated'))
@@ -214,9 +214,9 @@
</div>
@endif
<form wire:submit.prevent="updateAgent" class="mb-6 space-y-3">
<div class="mb-5 space-y-2">
<label class="block text-sm font-bold text-zinc-700 dark:text-zinc-200" for="show_agent_id">Assigned agent</label>
<select id="show_agent_id" wire:model.live="agent_id" class="hd-select block w-full rounded-xl border border-zinc-300 bg-white p-3 text-sm font-bold text-zinc-900 shadow-sm focus:border-emerald-500 focus:ring-emerald-500 dark:border-zinc-700 dark:bg-zinc-950 dark:text-zinc-100" data-dusk="ticket-show-agent">
<select id="show_agent_id" wire:model="agent_id" class="hd-select block w-full rounded-xl border border-zinc-300 bg-white px-3 py-2 text-sm font-semibold text-zinc-900 shadow-sm focus:border-emerald-500 focus:ring-emerald-500 dark:border-zinc-700 dark:bg-zinc-950 dark:text-zinc-100" data-dusk="ticket-show-agent">
<option value="">Unassigned</option>
@forelse ($agents as $agent)
<option value="{{ $agent->id }}">{{ $agent->name }} · {{ $agent->email }}</option>
@@ -225,42 +225,42 @@
@endforelse
</select>
@error('agent_id') <p class="text-sm font-bold text-red-600 dark:text-red-400">{{ $message }}</p> @enderror
<button type="submit" dusk="update-agent" class="inline-flex w-full items-center justify-center rounded-xl bg-emerald-600 px-4 py-2.5 text-sm font-black text-white shadow-sm transition hover:bg-emerald-700 focus:outline-none focus:ring-2 focus:ring-emerald-400/70 disabled:cursor-not-allowed disabled:opacity-70" wire:loading.attr="disabled" wire:target="updateAgent">
<button type="button" wire:click="updateAgent" dusk="update-agent" class="inline-flex w-full items-center justify-center rounded-lg bg-emerald-600 px-3 py-2 text-xs font-bold text-white shadow-sm transition hover:bg-emerald-700 focus:outline-none focus:ring-2 focus:ring-emerald-400/70 disabled:cursor-not-allowed disabled:opacity-70" wire:loading.attr="disabled" wire:target="updateAgent">
<i class="fa-solid fa-user-check mr-2" aria-hidden="true"></i>
<span wire:loading.remove wire:target="updateAgent">Assign agent</span>
<span wire:loading wire:target="updateAgent">Assigning...</span>
</button>
</form>
</div>
<form wire:submit.prevent="updateStatus" class="mb-6 space-y-3">
<div class="mb-5 space-y-2">
<label class="block text-sm font-bold text-zinc-700 dark:text-zinc-200" for="show_status_id">Status</label>
<select id="show_status_id" wire:model.live="status_id" class="hd-select block w-full rounded-xl border border-zinc-300 bg-white p-3 text-sm font-bold text-zinc-900 shadow-sm focus:border-blue-500 focus:ring-blue-500 dark:border-zinc-700 dark:bg-zinc-950 dark:text-zinc-100" data-dusk="ticket-show-status">
<select id="show_status_id" wire:model="status_id" class="hd-select block w-full rounded-xl border border-zinc-300 bg-white px-3 py-2 text-sm font-semibold text-zinc-900 shadow-sm focus:border-blue-500 focus:ring-blue-500 dark:border-zinc-700 dark:bg-zinc-950 dark:text-zinc-100" data-dusk="ticket-show-status">
@foreach ($statuses as $status)
<option value="{{ $status->id }}">{{ $status->name }}</option>
@endforeach
</select>
@error('status_id') <p class="text-sm font-bold text-red-600 dark:text-red-400">{{ $message }}</p> @enderror
<button type="submit" dusk="update-status" class="inline-flex w-full items-center justify-center rounded-xl bg-blue-600 px-4 py-2.5 text-sm font-black text-white shadow-sm transition hover:bg-blue-700 focus:outline-none focus:ring-2 focus:ring-blue-400/70 disabled:cursor-not-allowed disabled:opacity-70" wire:loading.attr="disabled" wire:target="updateStatus">
<button type="button" wire:click="updateStatus" dusk="update-status" class="inline-flex w-full items-center justify-center rounded-lg bg-blue-600 px-3 py-2 text-xs font-bold text-white shadow-sm transition hover:bg-blue-700 focus:outline-none focus:ring-2 focus:ring-blue-400/70 disabled:cursor-not-allowed disabled:opacity-70" wire:loading.attr="disabled" wire:target="updateStatus">
<i class="fa-solid fa-circle-check mr-2" aria-hidden="true"></i>
<span wire:loading.remove wire:target="updateStatus">Update status</span>
<span wire:loading wire:target="updateStatus">Updating...</span>
</button>
</form>
</div>
<form wire:submit.prevent="updatePriority" class="space-y-3">
<div class="space-y-2">
<label class="block text-sm font-bold text-zinc-700 dark:text-zinc-200" for="show_priority_id">Priority</label>
<select id="show_priority_id" wire:model.live="priority_id" class="hd-select block w-full rounded-xl border border-zinc-300 bg-white p-3 text-sm font-bold text-zinc-900 shadow-sm focus:border-amber-500 focus:ring-amber-500 dark:border-zinc-700 dark:bg-zinc-950 dark:text-zinc-100" data-dusk="ticket-show-priority">
<select id="show_priority_id" wire:model="priority_id" class="hd-select block w-full rounded-xl border border-zinc-300 bg-white px-3 py-2 text-sm font-semibold text-zinc-900 shadow-sm focus:border-amber-500 focus:ring-amber-500 dark:border-zinc-700 dark:bg-zinc-950 dark:text-zinc-100" data-dusk="ticket-show-priority">
@foreach ($priorities as $priority)
<option value="{{ $priority->id }}">{{ $priority->name }}</option>
@endforeach
</select>
@error('priority_id') <p class="text-sm font-bold text-red-600 dark:text-red-400">{{ $message }}</p> @enderror
<button type="submit" dusk="update-priority" class="inline-flex w-full items-center justify-center rounded-xl bg-amber-500 px-4 py-2.5 text-sm font-black text-white shadow-sm transition hover:bg-amber-600 focus:outline-none focus:ring-2 focus:ring-amber-300/70 disabled:cursor-not-allowed disabled:opacity-70" wire:loading.attr="disabled" wire:target="updatePriority">
<button type="button" wire:click="updatePriority" dusk="update-priority" class="inline-flex w-full items-center justify-center rounded-lg bg-amber-500 px-3 py-2 text-xs font-bold text-white shadow-sm transition hover:bg-amber-600 focus:outline-none focus:ring-2 focus:ring-amber-300/70 disabled:cursor-not-allowed disabled:opacity-70" wire:loading.attr="disabled" wire:target="updatePriority">
<i class="fa-solid fa-flag mr-2" aria-hidden="true"></i>
<span wire:loading.remove wire:target="updatePriority">Update priority</span>
<span wire:loading wire:target="updatePriority">Updating...</span>
</button>
</form>
</div>
</div>
@endcan
</aside>