Implement UPPER/LOWER; minor Fixes

This commit is contained in:
Pijus Kamandulis 2024-02-24 20:00:47 +02:00
parent f37c664c1a
commit f356f26d26
12 changed files with 394 additions and 183 deletions

1
go.mod
View File

@ -6,6 +6,7 @@ require (
github.com/Azure/azure-sdk-for-go/sdk/azcore v1.9.2 github.com/Azure/azure-sdk-for-go/sdk/azcore v1.9.2
github.com/Azure/azure-sdk-for-go/sdk/data/azcosmos v0.3.6 github.com/Azure/azure-sdk-for-go/sdk/data/azcosmos v0.3.6
github.com/gin-gonic/gin v1.9.1 github.com/gin-gonic/gin v1.9.1
github.com/google/uuid v1.1.1
github.com/stretchr/testify v1.8.4 github.com/stretchr/testify v1.8.4
) )

View File

@ -1,14 +1,15 @@
package repositories package repositories
import ( import (
"fmt"
"time"
"github.com/google/uuid"
repositorymodels "github.com/pikami/cosmium/internal/repository_models" repositorymodels "github.com/pikami/cosmium/internal/repository_models"
structhidrators "github.com/pikami/cosmium/internal/struct_hidrators" structhidrators "github.com/pikami/cosmium/internal/struct_hidrators"
) )
var collections = []repositorymodels.Collection{ var collections = []repositorymodels.Collection{}
{ID: "db1"},
{ID: "db2"},
}
func GetAllCollections(databaseId string) ([]repositorymodels.Collection, repositorymodels.RepositoryStatus) { func GetAllCollections(databaseId string) ([]repositorymodels.Collection, repositorymodels.RepositoryStatus) {
dbCollections := make([]repositorymodels.Collection, 0) dbCollections := make([]repositorymodels.Collection, 0)
@ -52,6 +53,9 @@ func CreateCollection(databaseId string, newCollection repositorymodels.Collecti
newCollection = structhidrators.Hidrate(newCollection).(repositorymodels.Collection) newCollection = structhidrators.Hidrate(newCollection).(repositorymodels.Collection)
newCollection.TimeStamp = time.Now().Unix()
newCollection.UniqueID = uuid.New().String()
newCollection.ETag = fmt.Sprintf("\"%s\"", newCollection.UniqueID)
newCollection.Internals = struct{ DatabaseId string }{ newCollection.Internals = struct{ DatabaseId string }{
DatabaseId: databaseId, DatabaseId: databaseId,
} }

View File

@ -1,6 +1,12 @@
package repositories package repositories
import repositorymodels "github.com/pikami/cosmium/internal/repository_models" import (
"fmt"
"time"
"github.com/google/uuid"
repositorymodels "github.com/pikami/cosmium/internal/repository_models"
)
var databases = []repositorymodels.Database{ var databases = []repositorymodels.Database{
{ID: "db1"}, {ID: "db1"},
@ -39,6 +45,9 @@ func CreateDatabase(newDatabase repositorymodels.Database) repositorymodels.Repo
} }
} }
newDatabase.TimeStamp = time.Now().Unix()
newDatabase.UniqueID = uuid.New().String()
newDatabase.ETag = fmt.Sprintf("\"%s\"", newDatabase.UniqueID)
databases = append(databases, newDatabase) databases = append(databases, newDatabase)
return repositorymodels.StatusOk return repositorymodels.StatusOk
} }

View File

@ -1,9 +1,12 @@
package repositories package repositories
import ( import (
"fmt"
"log" "log"
"strings" "strings"
"time"
"github.com/google/uuid"
repositorymodels "github.com/pikami/cosmium/internal/repository_models" repositorymodels "github.com/pikami/cosmium/internal/repository_models"
"github.com/pikami/cosmium/parsers" "github.com/pikami/cosmium/parsers"
"github.com/pikami/cosmium/parsers/nosql" "github.com/pikami/cosmium/parsers/nosql"
@ -93,6 +96,9 @@ func CreateDocument(databaseId string, collectionId string, document map[string]
partitionKeyValue = append(partitionKeyValue, val.(string)) partitionKeyValue = append(partitionKeyValue, val.(string))
} }
document["_ts"] = time.Now().Unix()
document["_rid"] = uuid.New().String()
document["_etag"] = fmt.Sprintf("\"%s\"", document["_rid"])
document["_internal"] = map[string]interface{}{ document["_internal"] = map[string]interface{}{
"databaseId": databaseId, "databaseId": databaseId,
"collectionId": collectionId, "collectionId": collectionId,

View File

@ -1,7 +1,10 @@
package repositorymodels package repositorymodels
type Database struct { type Database struct {
ID string `json:"id"` ID string `json:"id"`
TimeStamp int64 `json:"_ts"`
UniqueID string `json:"_rid"`
ETag string `json:"_etag"`
} }
type RepositoryStatus int type RepositoryStatus int
@ -17,10 +20,10 @@ type Collection struct {
ID string `json:"id"` ID string `json:"id"`
IndexingPolicy CollectionIndexingPolicy `json:"indexingPolicy"` IndexingPolicy CollectionIndexingPolicy `json:"indexingPolicy"`
PartitionKey CollectionPartitionKey `json:"partitionKey"` PartitionKey CollectionPartitionKey `json:"partitionKey"`
Rid string `json:"_rid"` UniqueID string `json:"_rid"`
Ts int `json:"_ts"` TimeStamp int64 `json:"_ts"`
Self string `json:"_self"` Self string `json:"_self"`
Etag string `json:"_etag"` ETag string `json:"_etag"`
Docs string `json:"_docs"` Docs string `json:"_docs"`
Sprocs string `json:"_sprocs"` Sprocs string `json:"_sprocs"`
Triggers string `json:"_triggers"` Triggers string `json:"_triggers"`

View File

@ -20,10 +20,10 @@ var defaultCollection repositorymodels.Collection = repositorymodels.Collection{
Kind: "Hash", Kind: "Hash",
Version: 2, Version: 2,
}, },
Rid: "nFFFFFFFFFF=", UniqueID: "nFFFFFFFFFF=",
Ts: 0, TimeStamp: 0,
Self: "", Self: "",
Etag: "\"00000000-0000-0000-0000-000000000000\"", ETag: "\"00000000-0000-0000-0000-000000000000\"",
Docs: "docs/", Docs: "docs/",
Sprocs: "sprocs/", Sprocs: "sprocs/",
Triggers: "triggers/", Triggers: "triggers/",

View File

@ -89,6 +89,8 @@ const (
FunctionCallIndexOf FunctionCallType = "IndexOf" FunctionCallIndexOf FunctionCallType = "IndexOf"
FunctionCallToString FunctionCallType = "ToString" FunctionCallToString FunctionCallType = "ToString"
FunctionCallIn FunctionCallType = "In" FunctionCallIn FunctionCallType = "In"
FunctionCallUpper FunctionCallType = "Upper"
FunctionCallLower FunctionCallType = "Lower"
) )
type FunctionCall struct { type FunctionCall struct {

File diff suppressed because it is too large Load Diff

View File

@ -312,6 +312,16 @@ StringFunctions <- StringEqualsExpression
/ ToStringExpression / ToStringExpression
/ ConcatExpression / ConcatExpression
/ ThreeArgumentStringFunctionExpression / ThreeArgumentStringFunctionExpression
/ UpperExpression
/ LowerExpression
UpperExpression <- "UPPER"i ws "(" ex:SelectItem ")" {
return parsers.FunctionCall{Type: parsers.FunctionCallUpper, Arguments: []interface{}{ex}}, nil
}
LowerExpression <- "LOWER"i ws "(" ex:SelectItem ")" {
return parsers.FunctionCall{Type: parsers.FunctionCallLower, Arguments: []interface{}{ex}}, nil
}
StringEqualsExpression <- StringEquals ws "(" ws ex1:SelectItem ws "," ws ex2:SelectItem ws ignoreCase:("," ws boolean:SelectItem { return boolean, nil })? ")" { StringEqualsExpression <- StringEquals ws "(" ws ex1:SelectItem ws "," ws ex2:SelectItem ws ignoreCase:("," ws boolean:SelectItem { return boolean, nil })? ")" {
return parsers.FunctionCall{Type: parsers.FunctionCallStringEquals, Arguments: []interface{}{ex1, ex2, ignoreCase}}, nil return parsers.FunctionCall{Type: parsers.FunctionCallStringEquals, Arguments: []interface{}{ex1, ex2, ignoreCase}}, nil

View File

@ -288,4 +288,52 @@ func Test_Execute_StringFunctions(t *testing.T) {
}, },
) )
}) })
t.Run("Should parse function UPPER()", func(t *testing.T) {
testQueryParse(
t,
`SELECT UPPER(c.id) FROM c`,
parsers.SelectStmt{
SelectItems: []parsers.SelectItem{
{
Type: parsers.SelectItemTypeFunctionCall,
Value: parsers.FunctionCall{
Type: parsers.FunctionCallUpper,
Arguments: []interface{}{
parsers.SelectItem{
Path: []string{"c", "id"},
Type: parsers.SelectItemTypeField,
},
},
},
},
},
Table: parsers.Table{Value: "c"},
},
)
})
t.Run("Should parse function LOWER()", func(t *testing.T) {
testQueryParse(
t,
`SELECT LOWER(c.id) FROM c`,
parsers.SelectStmt{
SelectItems: []parsers.SelectItem{
{
Type: parsers.SelectItemTypeFunctionCall,
Value: parsers.FunctionCall{
Type: parsers.FunctionCallLower,
Arguments: []interface{}{
parsers.SelectItem{
Path: []string{"c", "id"},
Type: parsers.SelectItemTypeField,
},
},
},
},
},
Table: parsers.Table{Value: "c"},
},
)
})
} }

View File

@ -190,6 +190,10 @@ func getFieldValue(field parsers.SelectItem, queryParameters map[string]interfac
return strings_IndexOf(typedValue.Arguments, queryParameters, row) return strings_IndexOf(typedValue.Arguments, queryParameters, row)
case parsers.FunctionCallToString: case parsers.FunctionCallToString:
return strings_ToString(typedValue.Arguments, queryParameters, row) return strings_ToString(typedValue.Arguments, queryParameters, row)
case parsers.FunctionCallUpper:
return strings_Upper(typedValue.Arguments, queryParameters, row)
case parsers.FunctionCallLower:
return strings_Lower(typedValue.Arguments, queryParameters, row)
case parsers.FunctionCallIsDefined: case parsers.FunctionCallIsDefined:
return typeChecking_IsDefined(typedValue.Arguments, queryParameters, row) return typeChecking_IsDefined(typedValue.Arguments, queryParameters, row)
case parsers.FunctionCallIn: case parsers.FunctionCallIn:

View File

@ -101,6 +101,16 @@ func strings_ToString(arguments []interface{}, queryParameters map[string]interf
return convertToString(value) return convertToString(value)
} }
func strings_Upper(arguments []interface{}, queryParameters map[string]interface{}, row RowType) string {
value := getFieldValue(arguments[0].(parsers.SelectItem), queryParameters, row)
return strings.ToUpper(convertToString(value))
}
func strings_Lower(arguments []interface{}, queryParameters map[string]interface{}, row RowType) string {
value := getFieldValue(arguments[0].(parsers.SelectItem), queryParameters, row)
return strings.ToLower(convertToString(value))
}
func getBoolFlag(arguments []interface{}, queryParameters map[string]interface{}, row RowType) bool { func getBoolFlag(arguments []interface{}, queryParameters map[string]interface{}, row RowType) bool {
ignoreCase := false ignoreCase := false
if len(arguments) > 2 && arguments[2] != nil { if len(arguments) > 2 && arguments[2] != nil {
@ -117,10 +127,10 @@ func parseString(argument interface{}, queryParameters map[string]interface{}, r
exItem := argument.(parsers.SelectItem) exItem := argument.(parsers.SelectItem)
ex := getFieldValue(exItem, queryParameters, row) ex := getFieldValue(exItem, queryParameters, row)
if str1, ok := ex.(string); ok { if str1, ok := ex.(string); ok {
fmt.Println("StringEquals got parameters of wrong type")
return str1 return str1
} }
fmt.Println("StringEquals got parameters of wrong type")
return "" return ""
} }