-
Notifications
You must be signed in to change notification settings - Fork 91
/
Copy pathkey_value.go
85 lines (69 loc) · 1.92 KB
/
key_value.go
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
package expmetric
import (
"encoding/json"
"expvar"
"strconv"
"github.com/kataras/iris/v12"
)
type (
// KeyFunc describes a handler which returns a key string.
KeyFunc func(ctx iris.Context) string
// ValueFunc describes a handler which returns a value and a boolean which
// allows or disallows the set of a variable.
ValueFunc func(ctx iris.Context) (interface{}, bool)
)
type directStringVar string
func (s directStringVar) String() string { return string(s) }
func convertValue(value interface{}) (expvar.Var, error) {
var valueVar expvar.Var
switch v := value.(type) {
case string:
valueVar = (directStringVar(strconv.Quote(v)))
case int64:
valueVar = directStringVar(strconv.Quote(strconv.FormatInt(v, 10)))
case expvar.Var: // same as fmt.Stringer.
valueVar = v
case json.Marshaler:
b, err := v.MarshalJSON()
if err != nil {
return nil, err
}
valueVar = directStringVar(string(b))
default:
expFunc := func() interface{} {
return value
}
valueVar = expvar.Func(expFunc)
}
return valueVar, nil
}
// KeyValue registers a Map expvar which is filled based on
// keyFunc and valueFunc input arguments.
// Supported values that a ValueFunc can return are:
// - string
// - int64
// - any value which completes the String() string method
// - any value which completes the json.Marshaler
// - any struct that can be displayed as JSON
// Look the "convertValue" function for details.
func KeyValue(keyFunc KeyFunc, valueFunc ValueFunc, options ...Option) iris.Handler {
opts := applyOptions(options)
if opts.MetricName == "" {
panic("iris: expmetric: metric name is empty")
}
expVar := expvar.NewMap(opts.MetricName)
return func(ctx iris.Context) {
if key := keyFunc(ctx); key != "" {
if value, ok := valueFunc(ctx); ok {
valueVar, err := convertValue(value)
if err != nil {
ctx.SetErr(err)
ctx.Next()
return
}
expVar.Set(key, valueVar)
}
}
ctx.Next()
}
}