Middle — Middle+
Come gestire le transazioni all'interno di un singolo metodo quando si utilizzano più operazioni transazionali, considerando il contesto di esecuzione?
sobes.tech AI
Risposta dell'AI
In Go, per gestire le transazioni all'interno di un metodo con più operazioni transazionali, si utilizza generalmente un oggetto di transazione ottenuto dal contesto del database (ad esempio, *sql.Tx). È importante passare questo oggetto a ogni funzione che esegue operazioni sul database, affinché tutte facciano parte di una stessa transazione.
Esempio:
func doComplexOperation(db *sql.DB) error {
tx, err := db.Begin()
if err != nil {
return err
}
defer func() {
if p := recover(); p != nil {
tx.Rollback()
panic(p)
} else if err != nil {
tx.Rollback()
} else {
err = tx.Commit()
}
}()
err = operation1(tx)
if err != nil {
return err
}
err = operation2(tx)
if err != nil {
return err
}
return nil
}
func operation1(tx *sql.Tx) error {
// Esecuzione di query SQL tramite tx.Exec o tx.Query
return nil
}
func operation2(tx *sql.Tx) error {
// Simile
return nil
}
In questo modo, tutte le operazioni vengono eseguite all'interno di una stessa transazione, e in caso di errore si effettua un rollback. Il contesto di esecuzione (context.Context) può essere usato per annullare o impostare un timeout, passando il contesto ai metodi di query, ma l'oggetto di transazione deve essere passato esplicitamente.