CodeGym /Corsi /SQL SELF /Analisi degli errori tipici quando si lavora con le strut...

Analisi degli errori tipici quando si lavora con le strutture di controllo e il logging

SQL SELF
Livello 52, Lezione 4
Disponibile

Prima di tutto, fermiamoci sugli errori e le sviste più frequenti che potresti incontrare. Gli errori in SQL sono il tormento di ogni dev, e di solito capitano proprio quando non dovrebbero.

1. Errori di sintassi: "mi sono dimenticato di chiudere IF"

Gli errori di sintassi sono i più basici, ma capitano più spesso di quanto pensi. Per esempio, se ti dimentichi di chiudere un blocco IF con END IF;, il compilatore ti bacchetta subito.

Esempio di errore:

CREATE OR REPLACE FUNCTION check_number(num INTEGER)
RETURNS TEXT AS $$
BEGIN
    IF num > 0 THEN
        RETURN 'Positivo';
    ELSE
        RETURN 'Negativo';
-- da qualche parte manca END IF;
END;
$$ LANGUAGE plpgsql;

Se provi a lanciare questo codice, ti becchi l’errore: ERROR: syntax error at or near "END". Perché? Perché il blocco IF è rimasto aperto.

Come evitare questi errori?

Usa sempre una struttura di codice chiara. Quando apri un blocco (tipo IF), scrivi subito anche la chiusura. Ecco la versione corretta:

CREATE OR REPLACE FUNCTION check_number(num INTEGER)
RETURNS TEXT AS $$
BEGIN
    IF num > 0 THEN
        RETURN 'Positivo';
    ELSE
        RETURN 'Negativo';
    END IF; -- non dimenticare di chiudere il blocco
END;
$$ LANGUAGE plpgsql;

2. Dimenticare di gestire tutti i casi nel CASE: "E se non rientro in nessun caso?"

Quando usi CASE, metti sempre il ramo ELSE per gestire comportamenti inaspettati. Se manca, rischi di beccarti un NULL non voluto.

Esempio di errore:

CREATE OR REPLACE FUNCTION grade_result(grade CHAR)
RETURNS TEXT AS $$
BEGIN
    RETURN CASE grade
        WHEN 'A' THEN 'Eccellente'
        WHEN 'B' THEN 'Buono'
        WHEN 'C' THEN 'Nella media'
        -- E se grade = 'D' o altro voto?
    END;
END;
$$ LANGUAGE plpgsql;

Se passi il valore D, la funzione ti restituisce NULL, e questo può creare problemi nel tuo codice.

Versione corretta:

CREATE OR REPLACE FUNCTION grade_result(grade CHAR)
RETURNS TEXT AS $$
BEGIN
    RETURN CASE grade
        WHEN 'A' THEN 'Eccellente'
        WHEN 'B' THEN 'Buono'
        WHEN 'C' THEN 'Nella media'
        ELSE 'Voto sconosciuto' -- Prendiamo tutti gli altri casi
    END;
END;
$$ LANGUAGE plpgsql;

3. Problemi con i cicli infiniti: "Perché il server si è bloccato?"

Quando usi il ciclo LOOP, è facile dimenticare la condizione di uscita. Così rischi di creare un ciclo infinito:

Esempio di errore:

CREATE OR REPLACE FUNCTION infinite_loop_demo()
RETURNS VOID AS $$
DECLARE
    i INTEGER := 1;
BEGIN
    LOOP
        i := i + 1;
        -- Nessuna condizione di uscita!
    END LOOP;
END;
$$ LANGUAGE plpgsql;

Questo codice manda in tilt il server perché il ciclo non finisce mai.

Come sistemare:

Aggiungi una condizione di uscita con EXIT:

CREATE OR REPLACE FUNCTION finite_loop_demo()
RETURNS VOID AS $$
DECLARE
    i INTEGER := 1;
BEGIN
    LOOP
        i := i + 1;
        IF i > 10 THEN
            EXIT; -- Condizione di uscita
        END IF;
    END LOOP;
END;
$$ LANGUAGE plpgsql;

4. Saltare iterazioni nei cicli: "E i dati mancanti?"

Quando usi CONTINUE per saltare delle iterazioni, puoi sbagliare se non consideri tutti i casi. Per esempio:

Esempio di errore:

CREATE OR REPLACE FUNCTION skip_even()
RETURNS VOID AS $$
DECLARE
    i INTEGER := 0;
BEGIN
    WHILE i < 10 LOOP
        i := i + 1;
        IF i % 2 = 0 THEN
            CONTINUE; -- Saltiamo i numeri pari
        END IF;
        RAISE NOTICE 'Numero dispari: %', i;
    END LOOP;
END;
$$ LANGUAGE plpgsql;

E se tutti i numeri fossero pari? Il server gira, ma non vedi nessun risultato.

Come sistemare:

Assicurati di gestire tutti i dati correttamente e aggiungi logging per controllare:

CREATE OR REPLACE FUNCTION skip_even_logging()
RETURNS VOID AS $$
DECLARE
    i INTEGER := 0;
BEGIN
    WHILE i < 10 LOOP
        i := i + 1;
        IF i % 2 = 0 THEN
            RAISE NOTICE 'Salto numero pari: %', i;
            CONTINUE;
        END IF;
        RAISE NOTICE 'Numero dispari: %', i;
    END LOOP;
END;
$$ LANGUAGE plpgsql;

Ora vedi quali numeri sono stati saltati.

5. Gestione errori sbagliata: "Dov'è il mio RAISE EXCEPTION?"

Gestire gli errori con RAISE EXCEPTION è una bomba, ma puoi fare casino se lo usi male.

Esempio di errore:

CREATE OR REPLACE FUNCTION calculate_square(num INTEGER)
RETURNS INTEGER AS $$
BEGIN
    IF num < 0 THEN
        RAISE 'Non è permesso un numero negativo!';
    END IF;
    RETURN num * num;
END;
$$ LANGUAGE plpgsql;

Questo codice dà errore perché la sintassi di RAISE è sbagliata (manca il livello del messaggio).

Versione corretta:

CREATE OR REPLACE FUNCTION calculate_square(num INTEGER)
RETURNS INTEGER AS $$
BEGIN
    IF num < 0 THEN
        RAISE EXCEPTION 'Non è permesso un numero negativo!';
    END IF;
    RETURN num * num;
END;
$$ LANGUAGE plpgsql;

6. Errori nel logging: "Perché i miei errori non finiscono in error_log?"

Scrivere male nella tabella error_log può succedere per errori nelle query INSERT INTO.

Esempio di errore:

CREATE OR REPLACE FUNCTION log_error(err_msg TEXT)
RETURNS VOID AS $$
BEGIN
    INSERT INTO error_log (error_message, error_time)
    VALUES (err_msg, CURRENT_TIMESTAMP); -- E se c'è un errore nei nomi delle colonne?
END;
$$ LANGUAGE plpgsql;

Se nella tabella error_log hai cambiato il nome della colonna (tipo in error_msg), ti becchi un errore.

Come evitare:

Controlla sempre la struttura della tabella o usa uno schema rigoroso per gestire i dati.

7. Disattenzione generale e "fattore umano"

Gli errori non sono solo tecnici, ma anche dovuti alla distrazione. Debug dimenticato, variabili inutilizzate o codice non formattato possono trasformare la tua funzione in un casino.

Esempio:

DECLARE
    i INTEGER; -- Perché, se la variabile non viene usata?

Soluzione: togli le parti inutili dal codice, così resta pulito e chiaro.

Ora sei pronto a evitare gli errori più comuni in PL/pgSQL e scrivere codice che dà più soddisfazione che mal di testa. Ricordati di testare, loggare e fixare i bug al volo — così ti risparmi un sacco di nervi e chiamate dai clienti!

2
Compito
SQL SELF, livello 52, lezione 4
Bloccato
Gestione di tutte le condizioni in `CASE`
Gestione di tutte le condizioni in `CASE`
1
Sondaggio/quiz
Gestione degli errori, livello 52, lezione 4
Non disponibile
Gestione degli errori
Gestione degli errori
Commenti
TO VIEW ALL COMMENTS OR TO MAKE A COMMENT,
GO TO FULL VERSION