147 lines
6.7 KiB
PHP
147 lines
6.7 KiB
PHP
<?php
|
|
|
|
namespace App\Http\Controllers;
|
|
|
|
// ─────────────────────────────────────────────────────────────────────────────
|
|
// CustomerController — CRUD completo per la gestione clienti
|
|
//
|
|
// CRUD = Create, Read, Update, Delete
|
|
//
|
|
// Laravel usa la convenzione "Resource Controller": 7 metodi standard
|
|
// che corrispondono alle operazioni CRUD via HTTP:
|
|
//
|
|
// index() → GET /customers → lista clienti
|
|
// create() → GET /customers/create → form nuovo cliente
|
|
// store() → POST /customers → salva nuovo cliente
|
|
// show() → GET /customers/{id} → dettaglio cliente
|
|
// edit() → GET /customers/{id}/edit → form modifica
|
|
// update() → PUT /customers/{id} → aggiorna cliente
|
|
// destroy() → DELETE /customers/{id} → elimina cliente
|
|
// ─────────────────────────────────────────────────────────────────────────────
|
|
|
|
use App\Models\Customer;
|
|
use App\Services\SettingService;
|
|
use Illuminate\Http\Request;
|
|
|
|
class CustomerController extends Controller
|
|
{
|
|
public function __construct(
|
|
private SettingService $settings
|
|
) {}
|
|
|
|
// ─── Lista clienti ─────────────────────────────────────────────────────
|
|
public function index(Request $request)
|
|
{
|
|
// Recupera il numero di elementi per pagina dalle impostazioni dinamiche
|
|
$perPage = $this->settings->get('items_per_page', 15);
|
|
|
|
// Costruisce la query con filtri opzionali dalla URL
|
|
// Es: /customers?search=mario&type=privato&status=attivo
|
|
$query = Customer::query();
|
|
|
|
if ($search = $request->input('search')) {
|
|
$query->search($search); // Usa lo scope definito nel Model
|
|
}
|
|
|
|
if ($type = $request->input('type')) {
|
|
$query->byType($type);
|
|
}
|
|
|
|
if ($status = $request->input('status')) {
|
|
$query->where('status', $status);
|
|
}
|
|
|
|
// paginate() divide i risultati in pagine e genera automaticamente
|
|
// i link prev/next, passati alla view come $customers->links()
|
|
$customers = $query->latest()->paginate($perPage)->withQueryString();
|
|
|
|
return view('customers.index', compact('customers'));
|
|
}
|
|
|
|
// ─── Form nuovo cliente ────────────────────────────────────────────────
|
|
public function create()
|
|
{
|
|
return view('customers.create');
|
|
}
|
|
|
|
// ─── Salva nuovo cliente ───────────────────────────────────────────────
|
|
public function store(Request $request)
|
|
{
|
|
// Validazione: se fallisce, Laravel reindirizza automaticamente
|
|
// al form precedente con gli errori e i valori inseriti.
|
|
$validated = $request->validate([
|
|
'name' => 'required|string|max:255',
|
|
'email' => 'required|email|unique:customers,email',
|
|
'phone' => 'nullable|string|max:50',
|
|
'city' => 'nullable|string|max:100',
|
|
'address' => 'nullable|string|max:255',
|
|
'vat_number' => 'nullable|string|max:20',
|
|
'fiscal_code' => 'nullable|string|max:20',
|
|
'type' => 'required|in:privato,azienda',
|
|
'status' => 'required|in:attivo,inattivo,prospect',
|
|
'notes' => 'nullable|string',
|
|
'contract_value' => 'nullable|numeric|min:0',
|
|
]);
|
|
|
|
$customer = Customer::create($validated);
|
|
|
|
// redirect() rimanda il browser a un'altra pagina
|
|
// with('success', ...) aggiunge un messaggio flash (mostrato una volta)
|
|
return redirect()
|
|
->route('customers.show', $customer)
|
|
->with('success', "Cliente \"{$customer->name}\" creato con successo.");
|
|
}
|
|
|
|
// ─── Dettaglio cliente ─────────────────────────────────────────────────
|
|
// Route Model Binding: Laravel trova automaticamente il Customer dall'URL
|
|
// Non serve scrivere: $customer = Customer::findOrFail($id);
|
|
public function show(Customer $customer)
|
|
{
|
|
return view('customers.show', compact('customer'));
|
|
}
|
|
|
|
// ─── Form modifica cliente ─────────────────────────────────────────────
|
|
public function edit(Customer $customer)
|
|
{
|
|
return view('customers.edit', compact('customer'));
|
|
}
|
|
|
|
// ─── Aggiorna cliente ─────────────────────────────────────────────────
|
|
public function update(Request $request, Customer $customer)
|
|
{
|
|
$validated = $request->validate([
|
|
'name' => 'required|string|max:255',
|
|
// unique: ignora il record corrente (altrimenti failerebbe sempre)
|
|
'email' => "required|email|unique:customers,email,{$customer->id}",
|
|
'phone' => 'nullable|string|max:50',
|
|
'city' => 'nullable|string|max:100',
|
|
'address' => 'nullable|string|max:255',
|
|
'vat_number' => 'nullable|string|max:20',
|
|
'fiscal_code' => 'nullable|string|max:20',
|
|
'type' => 'required|in:privato,azienda',
|
|
'status' => 'required|in:attivo,inattivo,prospect',
|
|
'notes' => 'nullable|string',
|
|
'contract_value' => 'nullable|numeric|min:0',
|
|
]);
|
|
|
|
$customer->update($validated);
|
|
|
|
return redirect()
|
|
->route('customers.show', $customer)
|
|
->with('success', "Cliente \"{$customer->name}\" aggiornato.");
|
|
}
|
|
|
|
// ─── Elimina cliente (soft delete) ────────────────────────────────────
|
|
// Grazie a SoftDeletes nel Model, il record non viene cancellato:
|
|
// viene impostato `deleted_at` e non compare più nelle query normali.
|
|
public function destroy(Customer $customer)
|
|
{
|
|
$name = $customer->name;
|
|
$customer->delete();
|
|
|
|
return redirect()
|
|
->route('customers.index')
|
|
->with('success', "Cliente \"{$name}\" eliminato.");
|
|
}
|
|
}
|