// Copyright (C) 2019 Storj Labs, Inc. // See LICENSE for copying information. package satellitedb import ( "context" "fmt" "github.com/zeebo/errs" ) //go:generate dbx.v1 schema -d postgres -d sqlite3 satellitedb.dbx . //go:generate dbx.v1 golang -d postgres -d sqlite3 satellitedb.dbx . func init() { // catch dbx errors class := errs.Class("satellitedb") WrapErr = func(e *Error) error { switch e.Code { case ErrorCode_NoRows: return e.Err case ErrorCode_ConstraintViolation: return class.Wrap(&constraintError{e.Constraint, e.Err}) } return class.Wrap(e) } } // Unwrap returns the underlying error. func (e *Error) Unwrap() error { return e.Err } // Cause returns the underlying error. func (e *Error) Cause() error { return e.Err } type constraintError struct { constraint string err error } // Unwrap returns the underlying error. func (err *constraintError) Unwrap() error { return err.err } // Cause returns the underlying error. func (err *constraintError) Cause() error { return err.err } // Error implements the error interface. func (err *constraintError) Error() string { return fmt.Sprintf("violates constraint %q: %v", err.constraint, err.err) } // WithTx wraps DB code in a transaction func (db *DB) WithTx(ctx context.Context, fn func(context.Context, *Tx) error) (err error) { tx, err := db.Open(ctx) if err != nil { return err } defer func() { if err == nil { err = tx.Commit() } else { err = errs.Combine(err, tx.Rollback()) } }() return fn(ctx, tx) }