feat: capture ASC and DESC

This commit is contained in:
Yehoshua Sandler 2025-04-15 16:41:27 -05:00
parent 68e3669c1a
commit ca5d403a3f
2 changed files with 70 additions and 22 deletions

View File

@ -1,7 +1,7 @@
package q package q
import ( import (
"fmt" // "fmt"
"strings" "strings"
"github.com/DataDog/go-sqllexer" "github.com/DataDog/go-sqllexer"
@ -19,7 +19,7 @@ type Select struct {
type OrderBy struct { type OrderBy struct {
Key string Key string
IsDescend bool IsDescend bool // SQL queries with no ASC|DESC on their ORDER BY are ASC by default, hence why this bool for the opposite
} }
func (q *Select) GetFullSql() string { func (q *Select) GetFullSql() string {
@ -61,7 +61,7 @@ func mutateSelectFromKeyword(query *Select, keyword string) {
} }
// TODO: make this an array of tokens instead // TODO: make this an array of tokens instead
func unshiftBuffer(buf *[10]string, value string) { func unshiftBuffer(buf *[10]sqllexer.Token, value sqllexer.Token) {
for i := 9; i >= 1; i-- { for i := 9; i >= 1; i-- {
buf[i] = buf[i-1] buf[i] = buf[i-1]
} }
@ -78,9 +78,11 @@ func ParseSelectStatement(sql string) Select {
passedTable := false passedTable := false
passedWHERE := false passedWHERE := false
passedConditionals := false passedConditionals := false
passedOrderBy := false passedOrderByKeywords := false
passesOrderByColumns := false
//checkForOrderDirection := false
lookBehindBuffer := [10]string{} // TODO: make this an array of tokens instead lookBehindBuffer := [10]sqllexer.Token{} // TODO: make this an array of tokens instead
var workingConditional = Conditional{} var workingConditional = Conditional{}
var columns []string var columns []string
@ -88,9 +90,6 @@ func ParseSelectStatement(sql string) Select {
lexer := sqllexer.New(sql) lexer := sqllexer.New(sql)
for { for {
token := lexer.Scan() token := lexer.Scan()
if IsTokenEndOfStatement(token) {
break
}
if !passedSELECT && strings.ToUpper(token.Value) != "SELECT" { if !passedSELECT && strings.ToUpper(token.Value) != "SELECT" {
break break
@ -125,11 +124,9 @@ func ParseSelectStatement(sql string) Select {
} }
} }
if !passedFROM && strings.ToUpper(token.Value) == "FROM" { if !passedFROM && strings.ToUpper(token.Value) == "FROM" { // TODO: make sure to check for other keywords that are allowed
passedFROM = true passedFROM = true
continue continue
} else if !passedFROM {
// continue // TODO: make sure to check for other keywords that are allowed
} }
if !passedTable && token.Type == sqllexer.IDENT { if !passedTable && token.Type == sqllexer.IDENT {
@ -165,21 +162,55 @@ func ParseSelectStatement(sql string) Select {
} }
// Checking For ORDER BY // Checking For ORDER BY
if !passedOrderBy && token.Type == sqllexer.KEYWORD { if !passedOrderByKeywords && token.Type == sqllexer.KEYWORD {
unshiftBuffer(&lookBehindBuffer, token.Value) unshiftBuffer(&lookBehindBuffer, *token)
if strings.ToUpper(lookBehindBuffer[1]) == "ORDER" && strings.ToUpper(lookBehindBuffer[0]) == "BY" { if strings.ToUpper(lookBehindBuffer[1].Value) == "ORDER" && strings.ToUpper(lookBehindBuffer[0].Value) == "BY" {
passedOrderBy = true passedOrderByKeywords = true
} }
fmt.Printf("VALUE: %s %s \n", lookBehindBuffer[1], lookBehindBuffer[0])
} }
if passedOrderBy && token.Type == sqllexer.IDENT { if passedOrderByKeywords && !passesOrderByColumns {
orderBys = append(orderBys, OrderBy{
Key: token.Value, // TODO: need to be able to get the ASC or DESC keyword too if token.Type == sqllexer.IDENT || token.Type == sqllexer.KEYWORD {
}) unshiftBuffer(&lookBehindBuffer, *token)
query.OrderBys = orderBys continue
}
if token.Type == sqllexer.PUNCTUATION || token.Type == sqllexer.EOF {
var orderByColumnName string
var directionKeyword string
var isDescend bool = false
if lookBehindBuffer[0].Type == sqllexer.KEYWORD {
orderByColumnName = lookBehindBuffer[1].Value
directionKeyword = lookBehindBuffer[0].Value
} else if lookBehindBuffer[0].Type == sqllexer.IDENT {
orderByColumnName = lookBehindBuffer[0].Value
}
if strings.ToUpper(directionKeyword) == "DESC" {
isDescend = true
}
orderBys = append(orderBys, OrderBy{
Key: orderByColumnName,
IsDescend: isDescend,
})
if IsTokenEndOfStatement(token) {
query.OrderBys = orderBys
break
}
}
}
query.OrderBys = orderBys
if IsTokenEndOfStatement(token) {
break
} }
} }

View File

@ -61,6 +61,23 @@ func TestParseSelectStatement(t *testing.T) {
}, },
}, },
}, },
{
input: "SELECT * FROM ZipCodes ORDER BY Code ASC, StateName DESC",
expected: Select{
Table: "ZipCodes",
IsWildcard: true,
OrderBys: []OrderBy{
{
Key: "Code",
IsDescend: false,
},
{
Key: "StateName",
IsDescend: true,
},
},
},
},
} }
for _, sql := range testSqlStatements { for _, sql := range testSqlStatements {