Skip to content

Commit

Permalink
Merge pull request #882 from ydb-platform/LevelSerializable
Browse files Browse the repository at this point in the history
* Allowed `sql.LevelSerializable` isolation level in read-write mode …
  • Loading branch information
asmyasnikov authored Oct 26, 2023
2 parents 4ae0dcb + da83f91 commit 5a37f51
Show file tree
Hide file tree
Showing 3 changed files with 32 additions and 12 deletions.
1 change: 1 addition & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
@@ -1,3 +1,4 @@
* Allowed `sql.LevelSerializable` isolation level in read-write mode in `database/sql` transactions
* Refactored traces and metrics
* Added `{retry,table}.WithLabel` options for mark retriers calls
* Added `ydb.WithTraceRetry` option
Expand Down
14 changes: 9 additions & 5 deletions internal/xsql/isolation/isolation.go
Original file line number Diff line number Diff line change
Expand Up @@ -15,11 +15,15 @@ import (
// It returns error on unsupported options.
func ToYDB(opts driver.TxOptions) (txcControl table.TxOption, err error) {
level := sql.IsolationLevel(opts.Isolation)
if !opts.ReadOnly && level == sql.LevelDefault {
return table.WithSerializableReadWrite(), nil
}
if opts.ReadOnly && level == sql.LevelSnapshot {
return table.WithSnapshotReadOnly(), nil
switch level {
case sql.LevelDefault, sql.LevelSerializable:
if !opts.ReadOnly {
return table.WithSerializableReadWrite(), nil
}
case sql.LevelSnapshot:
if opts.ReadOnly {
return table.WithSnapshotReadOnly(), nil
}
}
return nil, xerrors.WithStackTrace(fmt.Errorf(
"unsupported transaction options: %+v", opts,
Expand Down
29 changes: 22 additions & 7 deletions internal/xsql/isolation/isolation_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -3,23 +3,24 @@ package isolation
import (
"database/sql"
"database/sql/driver"
"fmt"
"testing"

"github.com/stretchr/testify/require"
"google.golang.org/protobuf/proto"

"github.com/ydb-platform/ydb-go-sdk/v3/internal/xtest"
"github.com/ydb-platform/ydb-go-sdk/v3/table"
)

func TestToYDB(t *testing.T) {
for _, tt := range []struct {
name string
txOptions driver.TxOptions
txControl table.TxOption
err bool
}{
// read-write
{
name: xtest.CurrentFileLine(),
txOptions: driver.TxOptions{
Isolation: driver.IsolationLevel(sql.LevelDefault),
ReadOnly: false,
Expand All @@ -28,48 +29,56 @@ func TestToYDB(t *testing.T) {
err: false,
},
{
name: xtest.CurrentFileLine(),
txOptions: driver.TxOptions{
Isolation: driver.IsolationLevel(sql.LevelReadUncommitted),
ReadOnly: false,
},
err: true,
},
{
name: xtest.CurrentFileLine(),
txOptions: driver.TxOptions{
Isolation: driver.IsolationLevel(sql.LevelReadCommitted),
ReadOnly: false,
},
err: true,
},
{
name: xtest.CurrentFileLine(),
txOptions: driver.TxOptions{
Isolation: driver.IsolationLevel(sql.LevelWriteCommitted),
ReadOnly: false,
},
err: true,
},
{
name: xtest.CurrentFileLine(),
txOptions: driver.TxOptions{
Isolation: driver.IsolationLevel(sql.LevelRepeatableRead),
ReadOnly: false,
},
err: true,
},
{
name: xtest.CurrentFileLine(),
txOptions: driver.TxOptions{
Isolation: driver.IsolationLevel(sql.LevelSnapshot),
ReadOnly: false,
},
err: true,
},
{
name: xtest.CurrentFileLine(),
txOptions: driver.TxOptions{
Isolation: driver.IsolationLevel(sql.LevelSerializable),
ReadOnly: false,
},
err: true,
txControl: table.WithSerializableReadWrite(),
err: false,
},
{
name: xtest.CurrentFileLine(),
txOptions: driver.TxOptions{
Isolation: driver.IsolationLevel(sql.LevelLinearizable),
ReadOnly: false,
Expand All @@ -79,41 +88,47 @@ func TestToYDB(t *testing.T) {

// read-only
{
name: xtest.CurrentFileLine(),
txOptions: driver.TxOptions{
Isolation: driver.IsolationLevel(sql.LevelDefault),
ReadOnly: true,
},
err: true,
},
{
name: xtest.CurrentFileLine(),
txOptions: driver.TxOptions{
Isolation: driver.IsolationLevel(sql.LevelReadUncommitted),
ReadOnly: true,
},
err: true,
},
{
name: xtest.CurrentFileLine(),
txOptions: driver.TxOptions{
Isolation: driver.IsolationLevel(sql.LevelReadCommitted),
ReadOnly: true,
},
err: true,
},
{
name: xtest.CurrentFileLine(),
txOptions: driver.TxOptions{
Isolation: driver.IsolationLevel(sql.LevelWriteCommitted),
ReadOnly: true,
},
err: true,
},
{
name: xtest.CurrentFileLine(),
txOptions: driver.TxOptions{
Isolation: driver.IsolationLevel(sql.LevelRepeatableRead),
ReadOnly: true,
},
err: true,
},
{
name: xtest.CurrentFileLine(),
txOptions: driver.TxOptions{
Isolation: driver.IsolationLevel(sql.LevelSnapshot),
ReadOnly: true,
Expand All @@ -122,27 +137,27 @@ func TestToYDB(t *testing.T) {
err: false,
},
{
name: xtest.CurrentFileLine(),
txOptions: driver.TxOptions{
Isolation: driver.IsolationLevel(sql.LevelSerializable),
ReadOnly: true,
},
err: true,
},
{
name: xtest.CurrentFileLine(),
txOptions: driver.TxOptions{
Isolation: driver.IsolationLevel(sql.LevelLinearizable),
ReadOnly: true,
},
err: true,
},
} {
t.Run(fmt.Sprintf("%+v", tt.txOptions), func(t *testing.T) {
t.Run(tt.name, func(t *testing.T) {
toYDB, err := ToYDB(tt.txOptions)
if !tt.err {
require.NoError(t, err)
if !proto.Equal(table.TxSettings(tt.txControl).Settings(), table.TxSettings(toYDB).Settings()) {
t.Errorf("%+v != %+v", toYDB, tt.txControl)
}
require.Equal(t, table.TxSettings(tt.txControl).Settings(), table.TxSettings(toYDB).Settings())
} else {
require.Error(t, err)
}
Expand Down

0 comments on commit 5a37f51

Please sign in to comment.