mirror of
https://github.com/ncruces/go-sqlite3.git
synced 2026-01-11 21:49:13 +00:00
199 lines
4.7 KiB
Go
199 lines
4.7 KiB
Go
package sqlite3
|
|
|
|
import (
|
|
"errors"
|
|
"fmt"
|
|
"strings"
|
|
"testing"
|
|
|
|
"github.com/ncruces/go-sqlite3/internal/util"
|
|
)
|
|
|
|
func Test_assertErr(t *testing.T) {
|
|
err := util.AssertErr()
|
|
if s := err.Error(); !strings.HasPrefix(s, "sqlite3: assertion failed") || !strings.HasSuffix(s, "error_test.go:13)") {
|
|
t.Errorf("got %q", s)
|
|
}
|
|
}
|
|
|
|
func TestError(t *testing.T) {
|
|
t.Parallel()
|
|
|
|
var ecode ErrorCode
|
|
var xcode xErrorCode
|
|
err := &Error{code: 0x8080}
|
|
if !errors.As(err, &err) {
|
|
t.Fatal("want true")
|
|
}
|
|
if ecode := err.Code(); ecode != 0x80 {
|
|
t.Errorf("got %#x, want 0x80", uint8(ecode))
|
|
}
|
|
if ok := errors.As(err, &ecode); !ok || ecode != ErrorCode(0x80) {
|
|
t.Errorf("got %#x, want 0x80", uint8(ecode))
|
|
}
|
|
if !errors.Is(err, ErrorCode(0x80)) {
|
|
t.Errorf("want true")
|
|
}
|
|
if xcode := err.ExtendedCode(); xcode != 0x8080 {
|
|
t.Errorf("got %#x, want 0x8080", uint16(xcode))
|
|
}
|
|
if ok := errors.As(err, &xcode); !ok || xcode != xErrorCode(0x8080) {
|
|
t.Errorf("got %#x, want 0x8080", uint16(xcode))
|
|
}
|
|
if !errors.Is(err, xErrorCode(0x8080)) {
|
|
t.Errorf("want true")
|
|
}
|
|
if s := err.Error(); s != "sqlite3: 32896" {
|
|
t.Errorf("got %q", s)
|
|
}
|
|
if ok := errors.As(err.ExtendedCode(), &ecode); !ok || ecode != ErrorCode(0x80) {
|
|
t.Errorf("got %#x, want 0x80", uint8(ecode))
|
|
}
|
|
if !errors.Is(err.ExtendedCode(), ErrorCode(0x80)) {
|
|
t.Errorf("want true")
|
|
}
|
|
}
|
|
|
|
func TestError_Temporary(t *testing.T) {
|
|
t.Parallel()
|
|
|
|
tests := []struct {
|
|
name string
|
|
code uint64
|
|
want bool
|
|
}{
|
|
{"ERROR", uint64(ERROR), false},
|
|
{"BUSY", uint64(BUSY), true},
|
|
{"BUSY_RECOVERY", uint64(BUSY_RECOVERY), true},
|
|
{"BUSY_SNAPSHOT", uint64(BUSY_SNAPSHOT), true},
|
|
{"BUSY_TIMEOUT", uint64(BUSY_TIMEOUT), true},
|
|
}
|
|
for _, tt := range tests {
|
|
t.Run(tt.name, func(t *testing.T) {
|
|
{
|
|
err := &Error{code: tt.code}
|
|
if got := err.Temporary(); got != tt.want {
|
|
t.Errorf("Error.Temporary(%d) = %v, want %v", tt.code, got, tt.want)
|
|
}
|
|
}
|
|
{
|
|
err := ErrorCode(tt.code)
|
|
if got := err.Temporary(); got != tt.want {
|
|
t.Errorf("ErrorCode.Temporary(%d) = %v, want %v", tt.code, got, tt.want)
|
|
}
|
|
}
|
|
{
|
|
err := ExtendedErrorCode(tt.code)
|
|
if got := err.Temporary(); got != tt.want {
|
|
t.Errorf("ExtendedErrorCode.Temporary(%d) = %v, want %v", tt.code, got, tt.want)
|
|
}
|
|
}
|
|
})
|
|
}
|
|
}
|
|
|
|
func TestError_Timeout(t *testing.T) {
|
|
t.Parallel()
|
|
|
|
tests := []struct {
|
|
name string
|
|
code uint64
|
|
want bool
|
|
}{
|
|
{"ERROR", uint64(ERROR), false},
|
|
{"BUSY", uint64(BUSY), false},
|
|
{"BUSY_RECOVERY", uint64(BUSY_RECOVERY), false},
|
|
{"BUSY_SNAPSHOT", uint64(BUSY_SNAPSHOT), false},
|
|
{"BUSY_TIMEOUT", uint64(BUSY_TIMEOUT), true},
|
|
}
|
|
for _, tt := range tests {
|
|
t.Run(tt.name, func(t *testing.T) {
|
|
{
|
|
err := &Error{code: tt.code}
|
|
if got := err.Timeout(); got != tt.want {
|
|
t.Errorf("Error.Timeout(%d) = %v, want %v", tt.code, got, tt.want)
|
|
}
|
|
}
|
|
{
|
|
err := ExtendedErrorCode(tt.code)
|
|
if got := err.Timeout(); got != tt.want {
|
|
t.Errorf("Error.Timeout(%d) = %v, want %v", tt.code, got, tt.want)
|
|
}
|
|
}
|
|
})
|
|
}
|
|
}
|
|
|
|
func Test_ErrorCode_Error(t *testing.T) {
|
|
t.Parallel()
|
|
|
|
db, err := Open(":memory:")
|
|
if err != nil {
|
|
t.Fatal(err)
|
|
}
|
|
defer db.Close()
|
|
|
|
// Test all error codes.
|
|
for i := 0; i == int(ErrorCode(i)); i++ {
|
|
want := "sqlite3: "
|
|
r := db.call("sqlite3_errstr", uint64(i))
|
|
want += util.ReadString(db.mod, uint32(r), _MAX_NAME)
|
|
|
|
got := ErrorCode(i).Error()
|
|
if got != want {
|
|
t.Fatalf("got %q, want %q, with %d", got, want, i)
|
|
}
|
|
}
|
|
}
|
|
|
|
func Test_ExtendedErrorCode_Error(t *testing.T) {
|
|
t.Parallel()
|
|
|
|
db, err := Open(":memory:")
|
|
if err != nil {
|
|
t.Fatal(err)
|
|
}
|
|
defer db.Close()
|
|
|
|
// Test all extended error codes.
|
|
for i := 0; i == int(ExtendedErrorCode(i)); i++ {
|
|
want := "sqlite3: "
|
|
r := db.call("sqlite3_errstr", uint64(i))
|
|
want += util.ReadString(db.mod, uint32(r), _MAX_NAME)
|
|
|
|
got := ExtendedErrorCode(i).Error()
|
|
if got != want {
|
|
t.Fatalf("got %q, want %q, with %d", got, want, i)
|
|
}
|
|
}
|
|
}
|
|
|
|
func Test_errorCode(t *testing.T) {
|
|
tests := []struct {
|
|
arg error
|
|
wantMsg string
|
|
wantCode uint32
|
|
}{
|
|
{nil, "", _OK},
|
|
{ERROR, "", util.ERROR},
|
|
{IOERR, "", util.IOERR},
|
|
{IOERR_READ, "", util.IOERR_READ},
|
|
{&Error{code: util.ERROR}, "", util.ERROR},
|
|
{fmt.Errorf("%w", ERROR), ERROR.Error(), util.ERROR},
|
|
{fmt.Errorf("%w", IOERR), IOERR.Error(), util.IOERR},
|
|
{fmt.Errorf("%w", IOERR_READ), IOERR_READ.Error(), util.IOERR_READ},
|
|
{fmt.Errorf("error"), "error", util.ERROR},
|
|
}
|
|
for _, tt := range tests {
|
|
t.Run("", func(t *testing.T) {
|
|
gotMsg, gotCode := errorCode(tt.arg, ERROR)
|
|
if gotMsg != tt.wantMsg {
|
|
t.Errorf("errorCode() gotMsg = %q, want %q", gotMsg, tt.wantMsg)
|
|
}
|
|
if gotCode != uint32(tt.wantCode) {
|
|
t.Errorf("errorCode() gotCode = %d, want %d", gotCode, tt.wantCode)
|
|
}
|
|
})
|
|
}
|
|
}
|