forked from stephenafamo/bob
-
Notifications
You must be signed in to change notification settings - Fork 0
/
Copy pathdebug_exec_test.go
130 lines (106 loc) · 2.95 KB
/
debug_exec_test.go
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
package bob
import (
"bytes"
"context"
"fmt"
"os"
"regexp"
"strconv"
"strings"
"testing"
)
var reArgs = regexp.MustCompile(`\n\d+\:`)
func TestDebugExecutorDefaultWriter(t *testing.T) {
d, ok := DebugToWriter(NoopExecutor{}, nil).(debugExecutor)
if !ok {
t.Fatal("DebugToWriter does not return an instance of debugExecutor")
}
writer, ok := d.printer.(writerPrinter)
if !ok {
t.Fatal("printer for debugExecutor is not a writerPrinter")
}
debugFile, ok := writer.Writer.(*os.File)
if !ok {
t.Fatal("writer for writerPrinter is not an *os.File")
}
if debugFile != os.Stdout {
t.Fatal("writer for debugExecutor is not os.Stdout")
}
}
func TestDebugExecutorDefaultPrinter(t *testing.T) {
d, ok := DebugToPrinter(NoopExecutor{}, nil).(debugExecutor)
if !ok {
t.Fatal("DebugExecutor does not return an instance of debugExecutor")
}
writer, ok := d.printer.(writerPrinter)
if !ok {
t.Fatal("printer for debugExecutor is not a writerPrinter")
}
debugFile, ok := writer.Writer.(*os.File)
if !ok {
t.Fatal("writer for writerPrinter is not an *os.File")
}
if debugFile != os.Stdout {
t.Fatal("writer for debugExecutor is not os.Stdout")
}
}
func TestDebugExecutor(t *testing.T) {
t.Run("QueryContext", func(t *testing.T) {
testDebugExecutor(t, func(exec Executor, s string, a ...any) error {
_, err := exec.QueryContext(context.Background(), s, a...)
if err != nil {
t.Fatal("error running QueryContext")
}
return err
})
})
t.Run("ExecContext", func(t *testing.T) {
testDebugExecutor(t, func(exec Executor, s string, a ...any) error {
_, err := exec.ExecContext(context.Background(), s, a...)
if err != nil {
t.Fatal("error running QueryContext")
}
return err
})
})
}
func testDebugExecutor(t *testing.T, f func(Executor, string, ...any) error) {
t.Helper()
dest := &bytes.Buffer{}
exec := DebugToWriter(NoopExecutor{}, dest)
sql := "A QUERY"
args := []any{"arg1", "arg2", "3rd arg"}
err := f(exec, sql, args...)
if err != nil {
t.Fatal(err)
}
debugsql, debugArgsStr, found := strings.Cut(dest.String(), "\n0:")
if !found {
t.Fatalf("arg delimiter not found in\n%s", dest.String())
}
if strings.TrimSpace(debugsql) != sql {
t.Fatalf("wrong debug sql.\nExpected: %s\nGot: %s", sql, strings.TrimSpace(debugsql))
}
var debugArgs []string //nolint:prealloc
for _, s := range reArgs.Split("\n0:"+debugArgsStr, -1) {
s := strings.TrimSpace(s)
if s == "" {
continue
}
unquoted, err := strconv.Unquote(s)
if err != nil {
t.Fatalf("could not unquote: %s", s)
}
debugArgs = append(debugArgs, unquoted)
}
if len(debugArgs) != len(args) {
t.Fatalf("wrong length of debug args.\nExpected: %d\nGot: %d\n\n%s", len(args), len(debugArgs), debugArgs)
}
for i := range args {
argStr := strings.TrimSpace(fmt.Sprint(args[i]))
debugStr := strings.TrimSpace(debugArgs[i])
if argStr != debugStr {
t.Fatalf("wrong debug arg %d.\nExpected: %s\nGot: %s", i, argStr, debugStr)
}
}
}