-
Notifications
You must be signed in to change notification settings - Fork 1
/
config_test.go
166 lines (135 loc) · 4.1 KB
/
config_test.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
164
165
166
package snakelet
import (
"reflect"
"strings"
"testing"
"github.com/CIDgravity/snakelet/testutil"
"github.com/spf13/afero"
"github.com/spf13/viper"
"github.com/stretchr/testify/require"
)
type DatabaseConfig struct {
User string `mapstructure:"user" validate:"required"`
Password string `mapstructure:"password" validate:"required"`
Host string `mapstructure:"host" validate:"required"`
Port int `mapstructure:"port" validate:"required"`
Name string `mapstructure:"name" validate:"required"`
SslMode string `mapstructure:"sslMode"`
MaxConns int `mapstructure:"maxConns"`
}
type LogsConfig struct {
LogLevel string `mapstructure:"level"` // error | warn | info - case insensitive
IsJson bool `mapstructure:"isJSON"`
SlowThreshold string `mapstructure:"databaseSlowThreshold"` // Value under which a query is considered slow. "1ms", "1s", etc - anything that's parsable by time.ParseDuration(interval).
}
type Config struct {
Database DatabaseConfig `mapstructure:"database"`
Logs LogsConfig `mapstructure:"log"`
Server ServerConfig `mapstructure:"server"`
}
type ServerConfig struct {
Port int `mapstructure:"port" validate:"required"`
}
// only set default for non-required tag
func GetDefaultConfig() *Config {
return &Config{
Database: DatabaseConfig{
SslMode: "disable",
MaxConns: 200,
},
Logs: LogsConfig{
LogLevel: "debug",
IsJson: false,
SlowThreshold: "1ms",
},
}
}
// Test that config init and load correctly with no config file
func TestInitAndLoadNoConfig(t *testing.T) {
conf := GetDefaultConfig()
_, err := InitAndLoad(conf, "")
if err == nil {
t.Fatalf(`Conf should return an error mentioning that some values are required!`)
}
if !strings.Contains(err.Error(), "required") {
t.Fatalf(`Conf should return an error mentioning that some values are required!: %e`, err)
}
}
func TestInitAndLoadCorrectConfig(t *testing.T) {
var yamlExample = []byte(`database:
user: test_user
password: "test_pwd"
host: test_host
name: test_name
port: "90"
server:
port: "90"
`)
fs := afero.NewMemMapFs()
fileDirectory := "/opt/viper"
filePath := fileDirectory + "/config.yml"
err := fs.Mkdir(testutil.AbsFilePath(t, fileDirectory), 0o777)
require.NoError(t, err)
_, err = fs.Create(testutil.AbsFilePath(t, filePath))
require.NoError(t, err)
err = afero.WriteFile(fs, testutil.AbsFilePath(t, filePath), yamlExample, 0644)
require.NoError(t, err)
// for testing purpose
viper.SetFs(fs)
conf := GetDefaultConfig()
_, err = InitAndLoad(conf, filePath)
if err != nil {
t.Fatalf(`Conf should not error: %e`, err)
}
// merge between default and config file's values
expectedModifiedConfStruct := &Config{
Database: DatabaseConfig{
User: "test_user",
Password: "test_pwd",
Host: "test_host",
Name: "test_name",
Port: 90,
SslMode: "disable",
MaxConns: 200,
},
Logs: LogsConfig{
LogLevel: "debug",
IsJson: false,
SlowThreshold: "1ms",
},
Server: ServerConfig{Port: 90},
}
if !reflect.DeepEqual(conf, expectedModifiedConfStruct) {
t.Fatalf(`Conf didn't unmarshal content from the file properly: %v & %v`, *conf, *expectedModifiedConfStruct)
}
}
func TestInitAndLoadWrongConfig(t *testing.T) {
var yamlExample = []byte(`database:
user: kdfj
password: djfkdls
host: dlkjf
name: value
port: should_be_a_number
server:
port: "90"
`)
fs := afero.NewMemMapFs()
fileDirectory := "/opt/viper"
filePath := fileDirectory + "/config.yml"
err := fs.Mkdir(testutil.AbsFilePath(t, fileDirectory), 0o777)
require.NoError(t, err)
_, err = fs.Create(testutil.AbsFilePath(t, filePath))
require.NoError(t, err)
err = afero.WriteFile(fs, testutil.AbsFilePath(t, filePath), yamlExample, 0644)
require.NoError(t, err)
// for testing purpose
viper.SetFs(fs)
conf := GetDefaultConfig()
_, err = InitAndLoad(conf, filePath)
if err == nil {
t.Fatalf(`Conf should be in error: %e`, err)
}
if !strings.Contains(err.Error(), "cannot parse 'database.port' as int") {
t.Fatalf(`Config should show specific error targeting database.port type: %e`, err)
}
}