Commit d869bd3f2ff89563ee389defeed535a204c7b150
1 parent
ab548c502b
Exists in
master
filtering fix
Showing
1 changed file
with
4 additions
and
2 deletions
Show diff stats
filtering.go
1 | package webutility | 1 | package webutility |
2 | 2 | ||
3 | import ( | 3 | import ( |
4 | "fmt" | 4 | "fmt" |
5 | "net/http" | 5 | "net/http" |
6 | "net/url" | ||
6 | "strings" | 7 | "strings" |
7 | ) | 8 | ) |
8 | 9 | ||
9 | type Filter map[string]string | 10 | type Filter map[string]string |
10 | 11 | ||
11 | func (f *Filter) Size() int { | 12 | func (f *Filter) Size() int { |
12 | return len(*f) | 13 | return len(*f) |
13 | } | 14 | } |
14 | 15 | ||
15 | func (f *Filter) Valid() bool { | 16 | func (f *Filter) Valid() bool { |
16 | return len(*f) > 0 | 17 | return len(*f) > 0 |
17 | } | 18 | } |
18 | 19 | ||
19 | func (fs Filter) validate(validFilters []string) (Filter, bool) { | 20 | func (fs Filter) validate(validFilters []string) (Filter, bool) { |
20 | goodFilters := make(map[string]string) | 21 | goodFilters := make(map[string]string) |
21 | cnt := 0 | 22 | cnt := 0 |
22 | len := 0 | 23 | len := 0 |
23 | for f, _ := range fs { | 24 | for f, _ := range fs { |
24 | len++ | 25 | len++ |
25 | for _, v := range validFilters { | 26 | for _, v := range validFilters { |
26 | if f == v { | 27 | if f == v { |
27 | cnt++ | 28 | cnt++ |
28 | goodFilters[f] = fs[f] | 29 | goodFilters[f] = fs[f] |
29 | } | 30 | } |
30 | } | 31 | } |
31 | } | 32 | } |
32 | 33 | ||
33 | result := true | 34 | result := true |
34 | if len > 0 && cnt == 0 { | 35 | if len > 0 && cnt == 0 { |
35 | // if no valid filters are found declare filtering request as invalid | 36 | // if no valid filters are found declare filtering request as invalid |
36 | result = false | 37 | result = false |
37 | } | 38 | } |
38 | 39 | ||
39 | return goodFilters, result | 40 | return goodFilters, result |
40 | } | 41 | } |
41 | 42 | ||
42 | // requires input in format: "param1::value1|param2::value2..." | 43 | // requires input in format: "param1::value1|param2::value2..." |
43 | func ParseFilters(req *http.Request, header string) (filters Filter) { | 44 | func ParseFilters(req *http.Request, header string) (filters Filter) { |
44 | q := req.FormValue(header) | 45 | q := req.FormValue(header) |
45 | q = strings.Trim(q, "\"") | 46 | q = strings.Trim(q, "\"") |
46 | kvp := strings.Split(q, "|") | 47 | kvp := strings.Split(q, "|") |
47 | filters = make(map[string]string, len(kvp)) | 48 | filters = make(map[string]string, len(kvp)) |
48 | 49 | ||
49 | for i, _ := range kvp { | 50 | for i, _ := range kvp { |
50 | kv := strings.Split(kvp[i], "::") | 51 | kv := strings.Split(kvp[i], "::") |
51 | if len(kv) == 2 { | 52 | if len(kv) == 2 { |
52 | key := kv[0] | 53 | key, _ := url.QueryUnescape(kv[0]) |
53 | val := kv[1] | 54 | val, _ := url.QueryUnescape(kv[1]) |
55 | fmt.Printf("%s: %s\n", key, val) | ||
54 | filters[key] = val | 56 | filters[key] = val |
55 | } | 57 | } |
56 | } | 58 | } |
57 | 59 | ||
58 | return filters | 60 | return filters |
59 | } | 61 | } |
60 | 62 | ||
61 | // TODO(marko): very dodgy, needs more robustness | 63 | // TODO(marko): very dodgy, needs more robustness |
62 | func MakeFilterString(prefix string, filters Filter, validFilters []string) (res string, ok bool) { | 64 | func MakeFilterString(prefix string, filters Filter, validFilters []string) (res string, ok bool) { |
63 | if prefix != "" { | 65 | if prefix != "" { |
64 | prefix += "." | 66 | prefix += "." |
65 | } | 67 | } |
66 | if len(filters) == 0 { | 68 | if len(filters) == 0 { |
67 | return "", true | 69 | return "", true |
68 | } | 70 | } |
69 | 71 | ||
70 | filters, ok = filters.validate(validFilters) | 72 | filters, ok = filters.validate(validFilters) |
71 | if !ok { | 73 | if !ok { |
72 | return "", ok | 74 | return "", ok |
73 | } | 75 | } |
74 | 76 | ||
75 | symbol := "=" | 77 | symbol := "=" |
76 | for k, v := range filters { | 78 | for k, v := range filters { |
77 | if res != "" { | 79 | if res != "" { |
78 | res += " and " | 80 | res += " and " |
79 | } else { | 81 | } else { |
80 | res += " where " | 82 | res += " where " |
81 | } | 83 | } |
82 | c := string(v[0]) | 84 | c := string(v[0]) |
83 | if c == "<" || c == ">" { | 85 | if c == "<" || c == ">" { |
84 | symbol = "" // examples: >3, >=3 | 86 | symbol = "" // examples: >3, >=3 |
85 | } else { | 87 | } else { |
86 | symbol = "=" | 88 | symbol = "=" |
87 | } | 89 | } |
88 | 90 | ||
89 | res += fmt.Sprintf("%s%s %s '%s'", prefix, k, symbol, v) | 91 | res += fmt.Sprintf("%s%s %s '%s'", prefix, k, symbol, v) |
90 | } | 92 | } |
91 | 93 | ||
92 | return res, ok | 94 | return res, ok |
93 | } | 95 | } |
94 | 96 |