Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

kvdb/postgres: remove global application level lock #7992

Closed
Closed
2 changes: 2 additions & 0 deletions kvdb/sqlbase/db.go
Original file line number Diff line number Diff line change
Expand Up @@ -308,6 +308,8 @@ func (db *db) executeTransaction(f func(tx walletdb.ReadWriteTx) error,
}

return err
continue
guggero marked this conversation as resolved.
Show resolved Hide resolved
}
}

dbErr := tx.Commit()
Expand Down
10 changes: 10 additions & 0 deletions kvdb/sqlbase/sqlerrors_postgres.go
Original file line number Diff line number Diff line change
Expand Up @@ -5,6 +5,7 @@ package sqlbase
import (
"errors"
"fmt"
"strings"

"github.com/jackc/pgconn"
"github.com/jackc/pgerrcode"
Expand All @@ -13,6 +14,15 @@ import (
// parsePostgresError attempts to parse a postgres error as a database agnostic
// SQL error.
func parsePostgresError(err error) error {
// Sometimes the error won't be properly wrapped, so we'll need to
// inspect raw error itself to detect something we can wrap properly.
const postgresErrMsg = "could not serialize access"
if strings.Contains(err.Error(), postgresErrMsg) {
return &ErrSerializationError{
DBError: err,
}
}

var pqErr *pgconn.PgError
if !errors.As(err, &pqErr) {
return nil
Expand Down
12 changes: 12 additions & 0 deletions kvdb/sqlbase/sqlerrors_sqlite.go
Original file line number Diff line number Diff line change
Expand Up @@ -5,6 +5,7 @@ package sqlbase
import (
"errors"
"fmt"
"strings"

"modernc.org/sqlite"
sqlite3 "modernc.org/sqlite/lib"
Expand All @@ -13,6 +14,17 @@ import (
// parseSqliteError attempts to parse a sqlite error as a database agnostic
// SQL error.
func parseSqliteError(err error) error {
// If the error isn't wrapped properly, the errors.As call with fail,
// so we'll also try to check the expected error message directly.
// This is taken from:
// https://gitlab.com/cznic/sqlite/-/blob/v1.25.0/sqlite.go#L75.
const sqliteErrMsg = "SQLITE_BUSY"
if strings.Contains(err.Error(), sqliteErrMsg) {
guggero marked this conversation as resolved.
Show resolved Hide resolved
return &ErrSerializationError{
DBError: err,
}
}

var sqliteErr *sqlite.Error
if !errors.As(err, &sqliteErr) {
return nil
Expand Down
21 changes: 21 additions & 0 deletions sqldb/sqlerrors.go
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,7 @@ package sqldb
import (
"errors"
"fmt"
"strings"

"github.com/jackc/pgconn"
"github.com/jackc/pgerrcode"
Expand Down Expand Up @@ -31,6 +32,26 @@ func MapSQLError(err error) error {
return parsePostgresError(pqErr)
}

// Sometimes the error won't be properly wrapped, so we'll need to
// inspect raw error itself to detect something we can wrap properly.
// This handles a postgres variant of the error.
const postgresErrMsg = "could not serialize access"
guggero marked this conversation as resolved.
Show resolved Hide resolved
if strings.Contains(err.Error(), postgresErrMsg) {
return &ErrSerializationError{
DBError: err,
}
}

// We'll also attempt to catch this for sqlite, that uses a slightly
// different error message. This is taken from:
// https://gitlab.com/cznic/sqlite/-/blob/v1.25.0/sqlite.go#L75.
const sqliteErrMsg = "SQLITE_BUSY"
if strings.Contains(err.Error(), sqliteErrMsg) {
return &ErrSerializationError{
DBError: err,
}
}

// Return original error if it could not be classified as a database
// specific error.
return err
Expand Down