Skip to content

Commit 853980b

Browse files
committed
WIP: add utils for building and printing the tree
1 parent 8114b4c commit 853980b

File tree

2 files changed

+67
-0
lines changed

2 files changed

+67
-0
lines changed

internal/db/db.go

Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -244,6 +244,15 @@ func readQueryResults(queryRows *sql.Rows, statementResultCh chan StatementResul
244244
}
245245

246246
func readQueryResultSet(queryRows *sql.Rows, statementResultCh chan StatementResult, query string) (shouldContinue bool) {
247+
if strings.Contains(query, "EXPLAIN") {
248+
root, err := BuildQueryPlanTree(queryRows)
249+
if err != nil {
250+
println("Failed to build tree")
251+
fmt.Printf("Error: %v \n", err)
252+
} else {
253+
PrintQueryPlanTree(root, "")
254+
}
255+
}
247256
columnNames, err := getColumnNames(queryRows)
248257
if err != nil {
249258
statementResultCh <- *newStatementResultWithError(err)

internal/db/explainTreeBuilder.go

Lines changed: 58 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,58 @@
1+
package db
2+
3+
import (
4+
"database/sql"
5+
"fmt"
6+
)
7+
8+
type QueryPlanNode struct {
9+
ID int
10+
ParentID int
11+
NotUsed int
12+
Detail string
13+
Children []*QueryPlanNode
14+
}
15+
16+
func BuildQueryPlanTree(rows *sql.Rows) (*QueryPlanNode, error) {
17+
var nodes []*QueryPlanNode
18+
nodeMap := make(map[int]*QueryPlanNode)
19+
20+
for rows.Next() {
21+
var id, parentID, notUsed int
22+
var detail string
23+
24+
err := rows.Scan(&id, &parentID, &notUsed, &detail)
25+
if err != nil {
26+
return nil, err
27+
}
28+
29+
node := &QueryPlanNode{
30+
ID: id,
31+
ParentID: parentID,
32+
NotUsed: notUsed,
33+
Detail: detail,
34+
}
35+
36+
nodes = append(nodes, node)
37+
nodeMap[id] = node
38+
}
39+
40+
root := &QueryPlanNode{}
41+
for _, node := range nodes {
42+
if node.ParentID == 0 {
43+
root = node
44+
} else {
45+
parent := nodeMap[node.ParentID]
46+
parent.Children = append(parent.Children, node)
47+
}
48+
}
49+
50+
return root, nil
51+
}
52+
53+
func PrintQueryPlanTree(node *QueryPlanNode, indent string) {
54+
fmt.Printf("%s%s\n", indent, node.Detail)
55+
for _, child := range node.Children {
56+
PrintQueryPlanTree(child, indent+" ")
57+
}
58+
}

0 commit comments

Comments
 (0)