In Java le eccezioni sono suddivise in checked (verificate) e unchecked (non verificate).
Exception, ma non da RuntimeException. Il compilatore richiede esplicitamente di gestirle con try-catch oppure di dichiararle in throws.RuntimeException. Il compilatore non richiede la loro gestione obbligatoria.public void readFile(String file) throws IOException { /* ... */ } // checked public void divide(int a, int b) { int res = a/b; } // unchecked (ArithmeticException)
La principale sottigliezza è che le checked exceptions vengono utilizzate per situazioni attese e recuperabili (ad esempio, errori di input-output), mentre le unchecked vengono utilizzate per errori di logica e situazioni critiche da cui non è possibile recuperare (ad esempio, NullPointerException).
Domanda: È necessario gestire o dichiarare in throws un'eccezione unchecked, se il tuo metodo può lanciarla?
Risposta: No. Il compilatore non richiede di controllare o dichiarare eccezioni non recuperabili (unchecked). La loro gestione è a tua discrezione; puoi utilizzare try-catch, ma più spesso — lasciare che "cada" fino al gestore globale.
public void foo() { throw new IllegalArgumentException(); } // Non richiede gestione o dichiarazione
Storia
Nel progetto dell'API bancaria, durante la gestione degli errori di input-output venivano lanciati
RuntimeExceptioninvece di checked. Di conseguenza, i clienti non erano obbligati a gestirli, il che portava a un funzionamento scorretto in caso di perdita di connessione con il server, e l'applicazione "cadeva" senza informare l'utente.
Storia
Uno sviluppatore ha dichiarato un numero eccessivo di
throws Exceptionnelle firme dei metodi (ad esempio, del database), il che ha costretto tutti i metodi utilizzati sopra a dover utilizzare try-catch o a dichiarare anche loro throws. Questo ha sporcato il codice, ha peggiorato la leggibilità e ha reso difficile il refactoring.
Storia
In uno dei microservizi venivano catturate tutte le eccezioni con un generico
catch (Exception e). Questo catturava anche le eccezioni unchecked (ad esempio,NullPointerException), il che portava a una "silenziosa" ignoranza di errori critici — il servizio lavorava con dati non corretti.