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
86
|
package envcfg
import (
"os"
"reflect"
"strconv"
"strings"
)
func getEnvName(n node) string {
name := n.properties.Tag.Get(TAG)
if name == "" {
name = n.properties.Name
}
abs, _ := strconv.ParseBool(n.properties.Tag.Get(ABS_TAG))
if !abs && n.parent != nil {
if n.parent.properties != nil {
parentName := getEnvName(*n.parent)
name = parentName + SEP + name
}
}
return strings.ToUpper(name)
}
func setValue(n node, v string) (node, error) {
switch n.value.Kind() {
case reflect.String:
n.value.SetString(v)
case reflect.Bool:
boolVal, err := strconv.ParseBool(v)
if err != nil {
return n, err
}
n.value.SetBool(boolVal)
case reflect.Int, reflect.Int8, reflect.Int16, reflect.Int32, reflect.Int64:
intVal, err := strconv.ParseInt(v, 0, n.value.Type().Bits())
if err != nil {
return n, err
}
n.value.SetInt(intVal)
case reflect.Float32, reflect.Float64:
floatVal, err := strconv.ParseFloat(v, n.value.Type().Bits())
if err != nil {
return n, err
}
n.value.SetFloat(floatVal)
}
return n, nil
}
func setFieldValue(n node) (node, error) {
if n.value.Kind() == reflect.Struct {
setStructFields(n)
return n, nil
}
v := os.Getenv(getEnvName(n))
if v != "" {
return setValue(n, v)
}
return n, nil
}
func setStructFields(n node) (node, []error) {
t := n.value.Type()
errs := []error{}
for i := 0; i < n.value.NumField(); i++ {
v := n.value.Field(i)
p := t.Field(i)
_, err := setFieldValue(node{&n, &v, &p})
if err != nil {
errs = append(errs, err)
}
}
return n, errs
}
|