netgescon-day0/app/Filament/Pages/Supporto/RichiestaHelp.php

202 lines
7.3 KiB
PHP

<?php
namespace App\Filament\Pages\Supporto;
use App\Models\CategoriaTicket;
use App\Models\Ticket;
use App\Models\TicketAttachment;
use App\Models\User;
use App\Support\StabileContext;
use BackedEnum;
use Filament\Forms\Components\FileUpload;
use Filament\Forms\Components\Select;
use Filament\Forms\Components\Textarea;
use Filament\Forms\Components\TextInput;
use Filament\Forms\Concerns\InteractsWithForms;
use Filament\Forms\Contracts\HasForms;
use Filament\Notifications\Notification;
use Filament\Pages\Page;
use Filament\Schemas\Schema;
use Illuminate\Support\Facades\Auth;
use Illuminate\Support\Facades\Process;
use Illuminate\Support\Facades\Storage;
use Livewire\WithFileUploads;
use UnitEnum;
class RichiestaHelp extends Page implements HasForms
{
use InteractsWithForms;
use WithFileUploads;
protected static ?string $navigationLabel = 'Richiedi help';
protected static ?string $title = 'Richiedi help / segnala bug';
protected static BackedEnum|string|null $navigationIcon = 'heroicon-o-lifebuoy';
protected static UnitEnum|string|null $navigationGroup = 'Supporto';
protected static ?int $navigationSort = 30;
protected static ?string $slug = 'supporto/richiesta-help';
protected string $view = 'filament.pages.supporto.richiesta-help';
public ?array $data = [];
public static function canAccess(): bool
{
$user = Auth::user();
return $user instanceof User
&& $user->hasAnyRole(['super-admin', 'admin', 'amministratore', 'collaboratore']);
}
public function mount(): void
{
$this->getSchema('form')?->fill([
'priorita' => 'Media',
]);
}
public function form(Schema $schema): Schema
{
return $schema
->statePath('data')
->components([
Select::make('tipo_richiesta')
->label('Tipo richiesta')
->options([
'bug' => 'Bug',
'implementazione' => 'Implementazione',
'modulo_nuovo' => 'Nuovo modulo',
'supporto_operativo' => 'Supporto operativo',
])
->default('supporto_operativo')
->required(),
TextInput::make('titolo')
->label('Titolo')
->required()
->maxLength(255),
Textarea::make('descrizione')
->label('Descrizione')
->required()
->rows(8),
Select::make('priorita')
->label('Priorità')
->options([
'Bassa' => 'Bassa',
'Media' => 'Media',
'Alta' => 'Alta',
'Urgente' => 'Urgente',
])
->required(),
Textarea::make('procedura_attivata')
->label('Procedura attivata / passi già fatti')
->rows(4)
->helperText('Inserisci i passaggi eseguiti, test fatti e risultato.'),
FileUpload::make('allegati')
->label('Foto / allegati')
->helperText('Da smartphone puoi scattare una foto al momento o selezionarla dalla galleria.')
->disk('public')
->directory('ticket-allegati')
->multiple()
->preserveFilenames()
->acceptedFileTypes([
'image/jpeg',
'image/png',
'image/webp',
'image/heic',
'image/heif',
])
->maxFiles(8)
->maxSize(12288),
]);
}
public function submit(): void
{
$user = Auth::user();
if (! $user instanceof User) {
abort(403);
}
$stabileId = StabileContext::resolveActiveStabileId($user);
if (! $stabileId) {
Notification::make()
->title('Seleziona prima uno stabile')
->danger()
->send();
return;
}
$state = $this->getSchema('form')?->getState() ?? [];
$gitBranch = trim((string) Process::path(base_path())->run('git rev-parse --abbrev-ref HEAD')->output());
$gitHash = trim((string) Process::path(base_path())->run('git rev-parse --short HEAD')->output());
$gitContext = 'Branch: ' . ($gitBranch !== '' ? $gitBranch : 'n/a') . ' | Commit: ' . ($gitHash !== '' ? $gitHash : 'n/a');
$tipoRichiesta = (string) ($state['tipo_richiesta'] ?? 'supporto_operativo');
$procedura = trim((string) ($state['procedura_attivata'] ?? ''));
$descrizioneBase = trim((string) ($state['descrizione'] ?? ''));
$descrizione = $descrizioneBase;
$descrizione .= "\n\n[Tracking Sviluppo]";
$descrizione .= "\nTipo richiesta: " . $tipoRichiesta;
$descrizione .= "\n" . $gitContext;
if ($procedura !== '') {
$descrizione .= "\nProcedura attivata: " . $procedura;
}
$categoria = CategoriaTicket::query()->firstOrCreate(
['nome' => 'Supporto'],
['descrizione' => 'Richieste help, bug e supporto operativo']
);
$ticket = Ticket::create([
'stabile_id' => $stabileId,
'aperto_da_user_id' => $user->id,
'categoria_ticket_id' => $categoria->id,
'titolo' => '[' . strtoupper($tipoRichiesta) . '] ' . (string) ($state['titolo'] ?? ''),
'descrizione' => $descrizione,
'priorita' => (string) ($state['priorita'] ?? 'Media'),
'stato' => 'Aperto',
]);
$allegati = $state['allegati'] ?? [];
if (is_array($allegati)) {
foreach ($allegati as $path) {
if (! is_string($path) || trim($path) === '') {
continue;
}
$disk = Storage::disk('public');
$mime = $disk->exists($path) ? $disk->mimeType($path) : null;
$size = $disk->exists($path) ? $disk->size($path) : null;
TicketAttachment::query()->create([
'ticket_id' => $ticket->id,
'ticket_update_id' => null,
'user_id' => $user->id,
'file_path' => $path,
'original_file_name' => basename($path),
'mime_type' => is_string($mime) ? $mime : null,
'size' => is_numeric($size) ? (int) $size : null,
'description' => 'Caricato in apertura ticket da Richiedi Help',
]);
}
}
$this->getSchema('form')?->fill([
'titolo' => null,
'descrizione' => null,
'tipo_richiesta' => 'supporto_operativo',
'priorita' => 'Media',
'procedura_attivata' => null,
'allegati' => [],
]);
Notification::make()
->title('Richiesta inviata')
->success()
->send();
}
}