This repository has been archived by the owner on Aug 31, 2021. It is now read-only.
-
Notifications
You must be signed in to change notification settings - Fork 0
/
config.go
163 lines (147 loc) · 4.48 KB
/
config.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
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
package config
import (
"sync"
)
var confWatch = configHolder{}
type configHolder struct {
lock sync.RWMutex
confItems []confItem
}
type confItem struct {
key string
ref interface{}
defValue interface{}
}
func (cc *configHolder) addRef(key string, ref interface{}, defValue interface{}) {
cc.lock.Lock()
defer cc.lock.Unlock()
cc.confItems = append(cc.confItems, confItem{key: key, ref: ref, defValue: defValue})
}
// RegisterString register an string variable
func RegisterString(key, defValue string) String { return confWatch.RegisterString(key, defValue) }
func (cc *configHolder) RegisterString(key, defValue string) String {
var v = defValue
cc.addRef(key, &v, defValue)
return stringHolder{value: &v}
}
// RegisterStringSlice register an string variable
func RegisterStringSlice(key string, defValue []string) StringSlice {
return confWatch.RegisterStringSlice(key, defValue)
}
func (cc *configHolder) RegisterStringSlice(key string, defValue []string) StringSlice {
var v = defValue
cc.addRef(key, &v, defValue)
return stringSliceHolder{value: &v}
}
// RegisterInt register an integer variable
func RegisterInt(key string, defValue int) Int { return confWatch.RegisterInt(key, defValue) }
func (cc *configHolder) RegisterInt(key string, defValue int) Int {
var v = int64(defValue)
cc.addRef(key, &v, defValue)
return intHolder{value: &v}
}
// RegisterInt64 register an int64 variable
func RegisterInt64(key string, defValue int64) Int { return confWatch.RegisterInt64(key, defValue) }
func (cc *configHolder) RegisterInt64(key string, defValue int64) Int {
var v = defValue
cc.addRef(key, &v, defValue)
return intHolder{value: &v}
}
// RegisterFloat32 register a float32 variable
func RegisterFloat32(key string, defValue float32) Float {
return confWatch.RegisterFloat32(key, defValue)
}
func (cc *configHolder) RegisterFloat32(key string, defValue float32) Float {
var v = float64(defValue)
cc.addRef(key, &v, defValue)
return floatHolder{value: &v}
}
// RegisterFloat64 register a float64 variable
func RegisterFloat64(key string, defValue float64) Float {
return confWatch.RegisterFloat64(key, defValue)
}
func (cc *configHolder) RegisterFloat64(key string, defValue float64) Float {
var v = defValue
cc.addRef(key, &v, defValue)
return floatHolder{value: &v}
}
// RegisterBool register a bool variable
func RegisterBool(key string, defValue bool) Bool { return confWatch.RegisterBool(key, defValue) }
func (cc *configHolder) RegisterBool(key string, defValue bool) Bool {
var v = defValue
cc.addRef(key, &v, defValue)
return boolHolder{value: &v}
}
func (cc *configHolder) handleChange() error {
cc.lock.RLock()
defer cc.lock.RUnlock()
for _, configItem := range cc.confItems {
switch configItem.defValue.(type) {
case string:
v, err := getViperString(configItem.key, configItem.defValue.(string))
if err != nil {
return err
}
t := configItem.ref.(*string)
*t = v
case []string:
v, err := getViperStringArray(configItem.key, configItem.defValue.([]string))
if err != nil {
return err
}
t := configItem.ref.(*[]string)
*t = v
case int:
v, err := getViperInt64(configItem.key, int64(configItem.defValue.(int)))
if err != nil {
return err
}
t := configItem.ref.(*int64)
*t = v
case int64:
v, err := getViperInt64(configItem.key, configItem.defValue.(int64))
if err != nil {
return err
}
t := configItem.ref.(*int64)
*t = v
case float32:
v, err := getViperFloat32(configItem.key, configItem.defValue.(float32))
if err != nil {
return err
}
t := configItem.ref.(*float32)
*t = v
case float64:
v, err := getViperFloat64(configItem.key, configItem.defValue.(float64))
if err != nil {
return err
}
t := configItem.ref.(*float64)
*t = v
case bool:
v, err := getViperBool(configItem.key, configItem.defValue.(bool))
if err != nil {
return err
}
t := configItem.ref.(*bool)
*t = v
}
}
return nil
}
// Load configs and set variables
// can use to reload configs
func Load() error {
return confWatch.handleChange()
}
// Init initialize config module with and accept confName that is config filename
// ext is config file extension
// appName is software name and will use to make search paths for config file
// config module will search for config files in flowing locations:
// /etc/<appName>
// $HOME/.<appName>
// and beside the executable file
func Init(confName, ext, appName string) error {
return initViper(confName, ext, appName, confWatch.handleChange)
}