File tree 10 files changed +206
-14
lines changed
10 files changed +206
-14
lines changed Original file line number Diff line number Diff line change @@ -14,11 +14,11 @@ import (
14
14
"log"
15
15
)
16
16
17
- var checker *ov.Checker
17
+ var checker *ov.ListChecker
18
18
19
19
func init() {
20
20
// Expect (int, int) or (float64, float64)
21
- checker = ov.NewChecker (
21
+ checker = ov.NewListChecker (
22
22
ov.NewRule(
23
23
ov.NewArgument("int"),
24
24
ov.NewArgument("int")),
@@ -63,11 +63,11 @@ import (
63
63
"log"
64
64
)
65
65
66
- var checker *ov.Checker
66
+ var checker *ov.ListChecker
67
67
68
68
func init() {
69
69
// Expect (int, int) or (int)
70
- checker = ov.NewChecker (
70
+ checker = ov.NewListChecker (
71
71
ov.NewRule(
72
72
ov.NewArgument("int"),
73
73
ov.NewArgument("int", 3)))
Original file line number Diff line number Diff line change 1
1
package overloading
2
2
3
3
type Argument struct {
4
- _type string
5
- _default interface {}
4
+ _type string
5
+ isOptional bool
6
+ _default interface {}
6
7
}
7
8
8
9
func NewArgument (args ... interface {}) * Argument {
@@ -23,6 +24,7 @@ func NewArgument(args ...interface{}) *Argument {
23
24
p ._type = arr [0 ].(string )
24
25
25
26
if len (arr ) == 2 {
27
+ p .isOptional = true
26
28
p ._default = arr [1 ]
27
29
}
28
30
@@ -34,7 +36,7 @@ func (a *Argument) Type() string {
34
36
}
35
37
36
38
func (a * Argument ) IsOptional () bool {
37
- return a ._default != nil
39
+ return a .isOptional
38
40
}
39
41
40
42
func (a * Argument ) Default () interface {} {
Original file line number Diff line number Diff line change 1
1
package overloading
2
2
3
- type Checker struct {
3
+ type ListChecker struct {
4
4
rules []* Rule
5
5
}
6
6
7
- func NewChecker (rules ... * Rule ) * Checker {
8
- c := new (Checker )
7
+ func NewListChecker (rules ... * Rule ) * ListChecker {
8
+ c := new (ListChecker )
9
9
c .rules = make ([]* Rule , len (rules ))
10
10
11
11
for i , r := range rules {
@@ -15,7 +15,7 @@ func NewChecker(rules ...*Rule) *Checker {
15
15
return c
16
16
}
17
17
18
- func (c * Checker ) Check (args []interface {}) []interface {} {
18
+ func (c * ListChecker ) Check (args []interface {}) []interface {} {
19
19
for _ , r := range c .rules {
20
20
out , err := r .Check (args )
21
21
if err == nil {
Original file line number Diff line number Diff line change @@ -9,7 +9,7 @@ func TestChecker(t *testing.T) {
9
9
t .Parallel ()
10
10
11
11
// Expect (int, int)
12
- c := NewChecker (
12
+ c := NewListChecker (
13
13
NewRule (
14
14
NewArgument ("int" ),
15
15
NewArgument ("int" )))
@@ -37,7 +37,7 @@ func TestCheckerViolation(t *testing.T) {
37
37
}()
38
38
39
39
// Expect (int, int)
40
- c := NewChecker (
40
+ c := NewListChecker (
41
41
NewRule (
42
42
NewArgument ("int" ),
43
43
NewArgument ("int" )))
@@ -58,7 +58,7 @@ func TestMultiRuleChecker(t *testing.T) {
58
58
t .Parallel ()
59
59
60
60
// Expect (int, int) or (float64, float64)
61
- c := NewChecker (
61
+ c := NewListChecker (
62
62
NewRule (
63
63
NewArgument ("int" ),
64
64
NewArgument ("int" )),
File renamed without changes.
File renamed without changes.
Original file line number Diff line number Diff line change
1
+ package overloading
2
+
3
+ type MapChecker struct {
4
+ rules []* MapRule
5
+ }
6
+
7
+ func NewMapChecker (args ... * MapRule ) * MapChecker {
8
+ m := new (MapChecker )
9
+ m .rules = make ([]* MapRule , len (args ))
10
+
11
+ for i , a := range args {
12
+ m .rules [i ] = a
13
+ }
14
+
15
+ return m
16
+ }
17
+
18
+ func (m * MapChecker ) Check (args map [string ]interface {}) map [string ]interface {} {
19
+ for _ , r := range m .rules {
20
+ out , err := r .Check (args )
21
+ if err == nil {
22
+ return out
23
+ }
24
+ }
25
+
26
+ panic ("No valid argument" )
27
+ }
Original file line number Diff line number Diff line change
1
+ package overloading
2
+
3
+ import (
4
+ "reflect"
5
+ "testing"
6
+ )
7
+
8
+ func TestMapChecker (t * testing.T ) {
9
+ c := NewMapChecker (
10
+ NewMapRule (
11
+ "x" , NewArgument ("int" ),
12
+ "y" , NewArgument ("int" )),
13
+ NewMapRule (
14
+ "x" , NewArgument ("float64" ),
15
+ "y" , NewArgument ("float64" )))
16
+
17
+ f := func (arg map [string ]interface {}) interface {} {
18
+ out := c .Check (arg )
19
+
20
+ t := reflect .TypeOf (out ["x" ]).String ()
21
+ switch t {
22
+ case "int" :
23
+ na := out ["x" ].(int )
24
+ nb := out ["y" ].(int )
25
+ return na + nb
26
+ case "float64" :
27
+ na := out ["x" ].(float64 )
28
+ nb := out ["y" ].(float64 )
29
+ return na + nb
30
+ default :
31
+ panic ("Unknown type" )
32
+ }
33
+ }
34
+
35
+ arg1 := make (map [string ]interface {})
36
+ arg1 ["x" ] = 3
37
+ arg1 ["y" ] = 2
38
+ if f (arg1 ).(int ) != 5 {
39
+ t .Error ("Wrong map checker" )
40
+ }
41
+
42
+ arg2 := make (map [string ]interface {})
43
+ arg2 ["x" ] = 3.0
44
+ arg2 ["y" ] = 2.0
45
+ if f (arg2 ).(float64 ) != 5.0 {
46
+ t .Error ("Wrong map checker" )
47
+ }
48
+ }
Original file line number Diff line number Diff line change
1
+ package overloading
2
+
3
+ import (
4
+ "errors"
5
+ "reflect"
6
+ )
7
+
8
+ type MapRule struct {
9
+ m map [string ]* Argument
10
+ }
11
+
12
+ func NewMapRule (args ... interface {}) * MapRule {
13
+ _len := len (args )
14
+ if _len % 2 != 0 {
15
+ panic ("Wrong argument length" )
16
+ }
17
+ r := new (MapRule )
18
+ r .m = make (map [string ]* Argument )
19
+
20
+ for i := 0 ; i < _len ; i += 2 {
21
+ k := args [i ].(string )
22
+ r .m [k ] = args [i + 1 ].(* Argument )
23
+ }
24
+
25
+ return r
26
+ }
27
+
28
+ func (r * MapRule ) Check (args map [string ]interface {}) (map [string ]interface {}, error ) {
29
+ out := make (map [string ]interface {})
30
+
31
+ for k , v := range args {
32
+ arg , ok := r .m [k ]
33
+ if ! ok {
34
+ return out , errors .New ("Unknown argument " + k )
35
+ }
36
+
37
+ t := reflect .TypeOf (v ).String ()
38
+ if t != arg .Type () {
39
+ return out , errors .New ("Wrong argument type on " + k )
40
+ }
41
+
42
+ out [k ] = v
43
+ }
44
+
45
+ for k := range r .m {
46
+ _ , ok := args [k ]
47
+ if ! ok {
48
+ if r .m [k ].IsOptional () {
49
+ out [k ] = r .m [k ].Default ()
50
+ } else {
51
+ return out , errors .New ("No default value on " + k )
52
+ }
53
+ }
54
+ }
55
+
56
+ return out , nil
57
+ }
Original file line number Diff line number Diff line change
1
+ package overloading
2
+
3
+ import "testing"
4
+
5
+ func TestMapRule (t * testing.T ) {
6
+ t .Parallel ()
7
+ r := NewMapRule (
8
+ "x" , NewArgument ("int" ),
9
+ "y" , NewArgument ("int" , 3 ))
10
+
11
+ f := func (arg map [string ]interface {}) int {
12
+ out , err := r .Check (arg )
13
+ if err != nil {
14
+ t .Error ("The argument should be correct" )
15
+ }
16
+
17
+ na := out ["x" ].(int )
18
+ nb := out ["y" ].(int )
19
+
20
+ return na + nb
21
+ }
22
+
23
+ args := make (map [string ]interface {})
24
+ args ["x" ] = 3
25
+
26
+ n := f (args )
27
+ if n != 6 {
28
+ t .Error ("Wrong rule" )
29
+ }
30
+ }
31
+
32
+ func TestMapRuleViolation (t * testing.T ) {
33
+ t .Parallel ()
34
+
35
+ r := NewMapRule (
36
+ "x" , NewArgument ("int" ),
37
+ "y" , NewArgument ("int" , 3 ))
38
+
39
+ f := func (arg map [string ]interface {}) int {
40
+ out , err := r .Check (arg )
41
+ if err == nil {
42
+ t .Error ("The argument should be wrong" )
43
+ } else {
44
+ return 0
45
+ }
46
+
47
+ na := out ["x" ].(int )
48
+ nb := out ["y" ].(int )
49
+
50
+ return na + nb
51
+ }
52
+
53
+ args := make (map [string ]interface {})
54
+ args ["x" ] = 3
55
+ args ["z" ] = 5
56
+
57
+ _ = f (args )
58
+ }
You can’t perform that action at this time.
0 commit comments