[wip] working on filters interface
This commit is contained in:
parent
8e45c45624
commit
4198ec4c75
|
@ -1,7 +1,21 @@
|
|||
package dal
|
||||
|
||||
type FindObject map[string]interface{}
|
||||
import (
|
||||
"fmt"
|
||||
"strings"
|
||||
|
||||
func CovertFind(findobj FindObject) string {
|
||||
return ""
|
||||
filters "l12.xyz/dal/filters"
|
||||
)
|
||||
|
||||
func CovertFind(find filters.Find, ctx filters.Context) string {
|
||||
expressions := []string{}
|
||||
for key, value := range find {
|
||||
values, err := filters.Convert(ctx.New(map[string]string{
|
||||
"FieldName": key,
|
||||
}), value)
|
||||
expressions = append(expressions, values)
|
||||
fmt.Println(err)
|
||||
|
||||
}
|
||||
return strings.Join(expressions, " AND ")
|
||||
}
|
||||
|
|
|
@ -1 +1,24 @@
|
|||
package dal
|
||||
|
||||
import (
|
||||
"testing"
|
||||
|
||||
f "l12.xyz/dal/filters"
|
||||
)
|
||||
|
||||
func TestConvertFind(t *testing.T) {
|
||||
find := f.Find{
|
||||
"test": "1",
|
||||
"test2": "2",
|
||||
"test3": f.Filter{
|
||||
"$ne": 1,
|
||||
},
|
||||
}
|
||||
ctx := f.SQLiteContext{
|
||||
TableAlias: "t",
|
||||
}
|
||||
result := CovertFind(find, ctx)
|
||||
if result != `t.test = '1'` {
|
||||
t.Errorf("Expected t.test = '1', got %s", result)
|
||||
}
|
||||
}
|
||||
|
|
|
@ -2,6 +2,12 @@ module l12.xyz/dal
|
|||
|
||||
go 1.22.6
|
||||
|
||||
require l12.xyz/dal/utils v0.0.0 // indirect
|
||||
|
||||
replace l12.xyz/dal/utils v0.0.0 => ../utils
|
||||
|
||||
require l12.xyz/dal/filters v0.0.0
|
||||
|
||||
require github.com/pkg/errors v0.9.1 // indirect
|
||||
|
||||
replace l12.xyz/dal/filters v0.0.0 => ../filters
|
||||
|
|
2
pkg/dal/go.sum
Normal file
2
pkg/dal/go.sum
Normal file
|
@ -0,0 +1,2 @@
|
|||
github.com/pkg/errors v0.9.1 h1:FEBLx1zS214owpjy7qsBeixbURkuhQAwrK5UwLGTwt4=
|
||||
github.com/pkg/errors v0.9.1/go.mod h1:bwawxfHBFNV+L2hUp1rHADufV3IMtnDRdf1r5NINEl0=
|
|
@ -17,6 +17,6 @@ func (f And) ToSQLPart(ctx Context) string {
|
|||
return fmt.Sprintf("(%s)", value)
|
||||
}
|
||||
|
||||
func (a And) FromJSON(data interface{}) Filter {
|
||||
func (a And) FromJSON(data interface{}) IFilter {
|
||||
return FromJson[And](data)
|
||||
}
|
||||
|
|
|
@ -10,7 +10,7 @@ type Between struct {
|
|||
Between []interface{} `json:"$between"`
|
||||
}
|
||||
|
||||
func (f Between) FromJSON(data interface{}) Filter {
|
||||
func (f Between) FromJSON(data interface{}) IFilter {
|
||||
return FromJson[Between](data)
|
||||
}
|
||||
|
||||
|
|
|
@ -8,7 +8,7 @@ type Eq struct {
|
|||
Eq interface{} `json:"$eq"`
|
||||
}
|
||||
|
||||
func (f Eq) FromJSON(data interface{}) Filter {
|
||||
func (f Eq) FromJSON(data interface{}) IFilter {
|
||||
return FromJson[Eq](data)
|
||||
}
|
||||
|
||||
|
|
|
@ -6,7 +6,7 @@ type Glob struct {
|
|||
Glob interface{} `json:"$glob"`
|
||||
}
|
||||
|
||||
func (f Glob) FromJSON(data interface{}) Filter {
|
||||
func (f Glob) FromJSON(data interface{}) IFilter {
|
||||
return FromJson[Glob](data)
|
||||
}
|
||||
|
||||
|
|
|
@ -8,7 +8,7 @@ type Gt struct {
|
|||
Gt interface{} `json:"$gt"`
|
||||
}
|
||||
|
||||
func (f Gt) FromJSON(data interface{}) Filter {
|
||||
func (f Gt) FromJSON(data interface{}) IFilter {
|
||||
return FromJson[Gt](data)
|
||||
}
|
||||
|
||||
|
|
|
@ -8,7 +8,7 @@ type Gte struct {
|
|||
Gte interface{} `json:"$gte"`
|
||||
}
|
||||
|
||||
func (f Gte) FromJSON(data interface{}) Filter {
|
||||
func (f Gte) FromJSON(data interface{}) IFilter {
|
||||
return FromJson[Gte](data)
|
||||
}
|
||||
|
||||
|
|
|
@ -11,7 +11,7 @@ type In struct {
|
|||
In []interface{} `json:"$in"`
|
||||
}
|
||||
|
||||
func (f In) FromJSON(data interface{}) Filter {
|
||||
func (f In) FromJSON(data interface{}) IFilter {
|
||||
return FromJson[In](data)
|
||||
}
|
||||
|
||||
|
|
|
@ -6,7 +6,7 @@ type Like struct {
|
|||
Like interface{} `json:"$like"`
|
||||
}
|
||||
|
||||
func (f Like) FromJSON(data interface{}) Filter {
|
||||
func (f Like) FromJSON(data interface{}) IFilter {
|
||||
return FromJson[Like](data)
|
||||
}
|
||||
|
||||
|
|
|
@ -8,7 +8,7 @@ type Lt struct {
|
|||
Lt interface{} `json:"$lt"`
|
||||
}
|
||||
|
||||
func (f Lt) FromJSON(data interface{}) Filter {
|
||||
func (f Lt) FromJSON(data interface{}) IFilter {
|
||||
return FromJson[Lt](data)
|
||||
}
|
||||
|
||||
|
|
|
@ -8,7 +8,7 @@ type Lte struct {
|
|||
Lte interface{} `json:"$lte"`
|
||||
}
|
||||
|
||||
func (f Lte) FromJSON(data interface{}) Filter {
|
||||
func (f Lte) FromJSON(data interface{}) IFilter {
|
||||
return FromJson[Lte](data)
|
||||
}
|
||||
|
||||
|
|
|
@ -6,7 +6,7 @@ type Ne struct {
|
|||
Ne interface{} `json:"$ne"`
|
||||
}
|
||||
|
||||
func (f Ne) FromJSON(data interface{}) Filter {
|
||||
func (f Ne) FromJSON(data interface{}) IFilter {
|
||||
return FromJson[Ne](data)
|
||||
}
|
||||
|
||||
|
|
|
@ -10,7 +10,7 @@ type NotBetween struct {
|
|||
NotBetween []interface{} `json:"$nbetween"`
|
||||
}
|
||||
|
||||
func (f NotBetween) FromJSON(data interface{}) Filter {
|
||||
func (f NotBetween) FromJSON(data interface{}) IFilter {
|
||||
return FromJson[NotBetween](data)
|
||||
}
|
||||
|
||||
|
|
|
@ -11,7 +11,7 @@ type NotIn struct {
|
|||
NotIn []interface{} `json:"$nin"`
|
||||
}
|
||||
|
||||
func (f NotIn) FromJSON(data interface{}) Filter {
|
||||
func (f NotIn) FromJSON(data interface{}) IFilter {
|
||||
return FromJson[NotIn](data)
|
||||
}
|
||||
|
||||
|
|
|
@ -6,7 +6,7 @@ type NotLike struct {
|
|||
NotLike interface{} `json:"$nlike"`
|
||||
}
|
||||
|
||||
func (f NotLike) FromJSON(data interface{}) Filter {
|
||||
func (f NotLike) FromJSON(data interface{}) IFilter {
|
||||
return FromJson[NotLike](data)
|
||||
}
|
||||
|
||||
|
|
|
@ -17,6 +17,6 @@ func (f Or) ToSQLPart(ctx Context) string {
|
|||
return fmt.Sprintf("(%s)", value)
|
||||
}
|
||||
|
||||
func (a Or) FromJSON(data interface{}) Filter {
|
||||
func (a Or) FromJSON(data interface{}) IFilter {
|
||||
return FromJson[Or](data)
|
||||
}
|
||||
|
|
|
@ -14,6 +14,21 @@ type SQLiteContext struct {
|
|||
FieldName string
|
||||
}
|
||||
|
||||
func (c SQLiteContext) New(opts map[string]string) Context {
|
||||
ta := opts["TableAlias"]
|
||||
if ta == "" {
|
||||
ta = c.TableAlias
|
||||
}
|
||||
fn := opts["FieldName"]
|
||||
if fn == "" {
|
||||
fn = c.FieldName
|
||||
}
|
||||
return SQLiteContext{
|
||||
TableAlias: ta,
|
||||
FieldName: fn,
|
||||
}
|
||||
}
|
||||
|
||||
func (c SQLiteContext) GetFieldName() string {
|
||||
if strings.Contains(c.FieldName, ".") {
|
||||
return c.FieldName
|
||||
|
|
|
@ -1,6 +1,10 @@
|
|||
package filters
|
||||
|
||||
var FilterRegistry = map[string]Filter{
|
||||
import (
|
||||
"reflect"
|
||||
)
|
||||
|
||||
var FilterRegistry = map[string]IFilter{
|
||||
"And": &And{},
|
||||
"Or": &Or{},
|
||||
"Eq": &Eq{},
|
||||
|
@ -18,12 +22,17 @@ var FilterRegistry = map[string]Filter{
|
|||
"NotLike": &NotLike{},
|
||||
}
|
||||
|
||||
func Convert(ctx Context, json interface{}) string {
|
||||
func Convert(ctx Context, data interface{}) (string, error) {
|
||||
for _, t := range FilterRegistry {
|
||||
value := t.FromJSON(json).ToSQLPart(ctx)
|
||||
filter := t.FromJSON(data)
|
||||
if reflect.DeepEqual(t, filter) {
|
||||
continue
|
||||
}
|
||||
value := filter.ToSQLPart(ctx)
|
||||
if value != "" {
|
||||
return value
|
||||
return value, nil
|
||||
}
|
||||
}
|
||||
return ""
|
||||
value := Eq{Eq: data}.ToSQLPart(ctx)
|
||||
return value, nil
|
||||
}
|
||||
|
|
|
@ -1,11 +1,17 @@
|
|||
package filters
|
||||
|
||||
type Context interface {
|
||||
New(opts map[string]string) Context
|
||||
GetFieldName() string
|
||||
NormalizeValue(interface{}) interface{}
|
||||
}
|
||||
|
||||
type Filter interface {
|
||||
type IFilter interface {
|
||||
ToSQLPart(ctx Context) string
|
||||
FromJSON(interface{}) Filter
|
||||
FromJSON(interface{}) IFilter
|
||||
}
|
||||
|
||||
type Find map[string]interface{}
|
||||
|
||||
// Filter{ "$eq": 1 }
|
||||
type Filter map[string]interface{}
|
||||
|
|
|
@ -9,8 +9,8 @@ func TestEq(t *testing.T) {
|
|||
TableAlias: "t",
|
||||
FieldName: "test",
|
||||
}
|
||||
result := Convert(ctx, `{"$eq": "NULL"}`)
|
||||
resultMap := Convert(ctx, map[string]any{"$eq": "NULL"})
|
||||
result, _ := Convert(ctx, `{"$eq": "NULL"}`)
|
||||
resultMap, _ := Convert(ctx, Filter{"$eq": "NULL"})
|
||||
if result != `t.test IS NULL` {
|
||||
t.Errorf("Expected t.test IS NULL, got %s", result)
|
||||
}
|
||||
|
@ -25,8 +25,8 @@ func TestGte(t *testing.T) {
|
|||
TableAlias: "t",
|
||||
FieldName: "test",
|
||||
}
|
||||
result := Convert(ctx, `{"$gte": 1}`)
|
||||
resultMap := Convert(ctx, map[string]any{"$gte": 1})
|
||||
result, _ := Convert(ctx, `{"$gte": 1}`)
|
||||
resultMap, _ := Convert(ctx, Filter{"$gte": 1})
|
||||
if result != `t.test >= 1` {
|
||||
t.Errorf("Expected t.test >= 1, got %s", result)
|
||||
}
|
||||
|
@ -40,8 +40,8 @@ func TestNe(t *testing.T) {
|
|||
ctx := SQLiteContext{
|
||||
FieldName: "test",
|
||||
}
|
||||
result := Convert(ctx, `{"$ne": "1"}`)
|
||||
resultMap := Convert(ctx, map[string]any{"$ne": "1"})
|
||||
result, _ := Convert(ctx, `{"$ne": "1"}`)
|
||||
resultMap, _ := Convert(ctx, Filter{"$ne": "1"})
|
||||
if result != `test != '1'` {
|
||||
t.Errorf("Expected test != '1', got %s", result)
|
||||
}
|
||||
|
@ -55,8 +55,8 @@ func TestBetween(t *testing.T) {
|
|||
ctx := SQLiteContext{
|
||||
FieldName: "test",
|
||||
}
|
||||
result := Convert(ctx, `{"$between": ["1", "5"]}`)
|
||||
resultMap := Convert(ctx, map[string]any{"$between": []string{"1", "5"}})
|
||||
result, _ := Convert(ctx, `{"$between": ["1", "5"]}`)
|
||||
resultMap, _ := Convert(ctx, Filter{"$between": []string{"1", "5"}})
|
||||
if result != `test BETWEEN '1' AND '5'` {
|
||||
t.Errorf("Expected test BETWEEN '1' AND '5', got %s", result)
|
||||
}
|
||||
|
@ -70,8 +70,8 @@ func TestNotBetween(t *testing.T) {
|
|||
ctx := SQLiteContext{
|
||||
FieldName: "test",
|
||||
}
|
||||
result := Convert(ctx, `{"$nbetween": ["1", "5"]}`)
|
||||
resultMap := Convert(ctx, map[string]any{"$nbetween": []string{"1", "5"}})
|
||||
result, _ := Convert(ctx, `{"$nbetween": ["1", "5"]}`)
|
||||
resultMap, _ := Convert(ctx, Filter{"$nbetween": []string{"1", "5"}})
|
||||
if result != `test NOT BETWEEN '1' AND '5'` {
|
||||
t.Errorf("Expected test BETWEEN '1' AND '5', got %s", result)
|
||||
}
|
||||
|
@ -86,8 +86,8 @@ func TestGlob(t *testing.T) {
|
|||
TableAlias: "t",
|
||||
FieldName: "test",
|
||||
}
|
||||
result := Convert(ctx, `{"$glob": "*son"}`)
|
||||
resultMap := Convert(ctx, map[string]any{"$glob": "*son"})
|
||||
result, _ := Convert(ctx, `{"$glob": "*son"}`)
|
||||
resultMap, _ := Convert(ctx, Filter{"$glob": "*son"})
|
||||
if result != `t.test GLOB '*son'` {
|
||||
t.Errorf("Expected t.test GLOB '*son', got %s", result)
|
||||
}
|
||||
|
@ -102,8 +102,8 @@ func TestIn(t *testing.T) {
|
|||
TableAlias: "t",
|
||||
FieldName: "test",
|
||||
}
|
||||
result := Convert(ctx, `{"$in": [1, 2, 3]}`)
|
||||
resultMap := Convert(ctx, map[string]any{"$in": []int{1, 2, 3}})
|
||||
result, _ := Convert(ctx, `{"$in": [1, 2, 3]}`)
|
||||
resultMap, _ := Convert(ctx, Filter{"$in": []int{1, 2, 3}})
|
||||
if result != `t.test IN (1, 2, 3)` {
|
||||
t.Errorf("Expected t.test IN (1, 2, 3), got %s", result)
|
||||
}
|
||||
|
@ -118,8 +118,8 @@ func TestNotIn(t *testing.T) {
|
|||
TableAlias: "t",
|
||||
FieldName: "test",
|
||||
}
|
||||
result := Convert(ctx, `{"$nin": [1, 2, 3]}`)
|
||||
resultMap := Convert(ctx, map[string]any{"$nin": []int{1, 2, 3}})
|
||||
result, _ := Convert(ctx, `{"$nin": [1, 2, 3]}`)
|
||||
resultMap, _ := Convert(ctx, Filter{"$nin": []int{1, 2, 3}})
|
||||
if result != `t.test NOT IN (1, 2, 3)` {
|
||||
t.Errorf("Expected t.test NOT IN (1, 2, 3), got %s", result)
|
||||
}
|
||||
|
@ -134,8 +134,8 @@ func TestLike(t *testing.T) {
|
|||
TableAlias: "t",
|
||||
FieldName: "test",
|
||||
}
|
||||
result := Convert(ctx, `{"$like": "199_"}`)
|
||||
resultMap := Convert(ctx, map[string]any{"$like": "199_"})
|
||||
result, _ := Convert(ctx, `{"$like": "199_"}`)
|
||||
resultMap, _ := Convert(ctx, Filter{"$like": "199_"})
|
||||
if result != `t.test LIKE '199_' ESCAPE '\'` {
|
||||
t.Errorf("Expected t.test LIKE '199_' ESCAPE '\\', got %s", result)
|
||||
}
|
||||
|
@ -150,8 +150,8 @@ func TestAnd(t *testing.T) {
|
|||
TableAlias: "t",
|
||||
FieldName: "test",
|
||||
}
|
||||
result := Convert(ctx, `{"$and": ["a > 0", "b < 10"]}`)
|
||||
resultMap := Convert(ctx, map[string]any{"$and": []string{"a > 0", "b < 10"}})
|
||||
result, _ := Convert(ctx, `{"$and": ["a > 0", "b < 10"]}`)
|
||||
resultMap, _ := Convert(ctx, Filter{"$and": []string{"a > 0", "b < 10"}})
|
||||
if result != `(a > 0 AND b < 10)` {
|
||||
t.Errorf("Expected (a > 0 AND b < 10), got %s", result)
|
||||
}
|
||||
|
@ -166,8 +166,8 @@ func TestOr(t *testing.T) {
|
|||
TableAlias: "t",
|
||||
FieldName: "test",
|
||||
}
|
||||
result := Convert(ctx, `{"$or": ["a = 0", "b < 10"]}`)
|
||||
resultMap := Convert(ctx, map[string]any{"$or": []string{"a = 0", "b < 10"}})
|
||||
result, _ := Convert(ctx, `{"$or": ["a = 0", "b < 10"]}`)
|
||||
resultMap, _ := Convert(ctx, Filter{"$or": []string{"a = 0", "b < 10"}})
|
||||
if result != `(a = 0 OR b < 10)` {
|
||||
t.Errorf("Expected (a > 0 OR b < 10), got %s", result)
|
||||
}
|
||||
|
|
|
@ -4,25 +4,25 @@ import (
|
|||
"encoding/json"
|
||||
)
|
||||
|
||||
func FromJson[T Filter](data interface{}) *T {
|
||||
func FromJson[T IFilter](data interface{}) *T {
|
||||
var t T
|
||||
str, ok := data.(string)
|
||||
if ok {
|
||||
err := json.Unmarshal([]byte(str), &t)
|
||||
if err != nil {
|
||||
return nil
|
||||
return &t
|
||||
}
|
||||
}
|
||||
m, ok := data.(map[string]interface{})
|
||||
m, ok := data.(Filter)
|
||||
if ok {
|
||||
s, err := json.Marshal(m)
|
||||
if err != nil {
|
||||
return nil
|
||||
return &t
|
||||
}
|
||||
|
||||
e := json.Unmarshal(s, &t)
|
||||
if e != nil {
|
||||
return nil
|
||||
return &t
|
||||
}
|
||||
}
|
||||
return &t
|
||||
|
|
Loading…
Reference in a new issue