-
Notifications
You must be signed in to change notification settings - Fork 0
Expand file tree
/
Copy pathparser_test.go
More file actions
125 lines (107 loc) · 3.86 KB
/
parser_test.go
File metadata and controls
125 lines (107 loc) · 3.86 KB
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
package parser
import (
"bytes"
"context"
"encoding/json"
"flag"
"os"
"path/filepath"
"testing"
)
type testMetadata struct {
Todo bool `json:"todo"`
InvalidSyntax bool `json:"invalid_syntax"`
}
// Test flag for running todo tests and auto-enabling passing ones
// Usage: go test ./parser/... -check-todo # run todo tests and auto-update metadata.json for passing tests
var checkTodoTests = flag.Bool("check-todo", false, "run todo tests and auto-update metadata.json for passing tests")
func TestParse(t *testing.T) {
entries, err := os.ReadDir("testdata")
if err != nil {
t.Fatalf("failed to read testdata directory: %v", err)
}
for _, entry := range entries {
if !entry.IsDir() {
continue
}
testName := entry.Name()
t.Run(testName, func(t *testing.T) {
testDir := filepath.Join("testdata", testName)
// Check metadata.json for todo/invalid_syntax flags
metadataPath := filepath.Join(testDir, "metadata.json")
metadataData, err := os.ReadFile(metadataPath)
if err != nil {
t.Fatalf("failed to read metadata.json: %v", err)
}
var metadata testMetadata
if err := json.Unmarshal(metadataData, &metadata); err != nil {
t.Fatalf("failed to parse metadata.json: %v", err)
}
// Skip tests marked with todo or invalid_syntax unless running with -check-todo
shouldSkip := metadata.Todo || metadata.InvalidSyntax
if shouldSkip && !*checkTodoTests {
t.Skip("skipped via metadata.json (todo or invalid_syntax)")
}
if !shouldSkip && *checkTodoTests {
t.Skip("not a todo/invalid_syntax test")
}
// For -check-todo, track if the test passes to update metadata (only for todo, not invalid_syntax)
checkTodoMode := *checkTodoTests && metadata.Todo && !metadata.InvalidSyntax
// Read the test SQL file
sqlPath := filepath.Join(testDir, "query.sql")
sqlData, err := os.ReadFile(sqlPath)
if err != nil {
t.Fatalf("failed to read SQL file: %v", err)
}
// Parse the SQL
ctx := context.Background()
script, err := Parse(ctx, bytes.NewReader(sqlData))
if err != nil {
t.Fatalf("Parse failed: %v", err)
}
// Marshal to JSON
gotJSON, err := MarshalScript(script)
if err != nil {
t.Fatalf("MarshalScript failed: %v", err)
}
// Read expected JSON
expectedPath := filepath.Join(testDir, "ast.json")
expectedJSON, err := os.ReadFile(expectedPath)
if err != nil {
t.Fatalf("failed to read expected JSON: %v", err)
}
// Normalize both JSONs for comparison
var gotObj, expectedObj any
if err := json.Unmarshal(gotJSON, &gotObj); err != nil {
t.Fatalf("failed to unmarshal got JSON: %v", err)
}
if err := json.Unmarshal(expectedJSON, &expectedObj); err != nil {
t.Fatalf("failed to unmarshal expected JSON: %v", err)
}
// Re-marshal for consistent formatting
gotNormalized, _ := json.MarshalIndent(gotObj, "", " ")
expectedNormalized, _ := json.MarshalIndent(expectedObj, "", " ")
if string(gotNormalized) != string(expectedNormalized) {
t.Errorf("JSON mismatch:\ngot:\n%s\n\nexpected:\n%s", gotNormalized, expectedNormalized)
}
// If running with -check-todo and the test passed, update metadata.json to remove todo flag
if checkTodoMode && !t.Failed() {
// Re-parse as map to preserve any extra fields
var metadataMap map[string]any
if err := json.Unmarshal(metadataData, &metadataMap); err != nil {
t.Errorf("failed to parse metadata.json as map: %v", err)
} else {
delete(metadataMap, "todo")
updatedMetadata, err := json.MarshalIndent(metadataMap, "", " ")
if err != nil {
t.Errorf("failed to marshal metadata: %v", err)
} else if err := os.WriteFile(metadataPath, append(updatedMetadata, '\n'), 0644); err != nil {
t.Errorf("failed to update metadata.json: %v", err)
} else {
t.Logf("ENABLED: updated %s (removed todo flag)", metadataPath)
}
}
}
})
}
}