Viper的使用方法
一、背景
Viper是适用于Go应用程序(包括Twelve-Factor App)的完整配置解决方案。它被设计用于在应用程序中工作,并且可以处理所有类型的配置需求和格式。它支持以下特性:
(1)设置默认值
(2)从JSON、TOML、YAML、HCL、envfile和Java properties格式的配置文件读取配置信息
(3)实时监控和重新读取配置文件(可选)
(4)从环境变量中读取
(5)从远程配置系统(etcd或Consul)读取并监控配置变化
(6)从命令行参数读取配置
(7)从buffer读取配置
(8)显式配置值
包的引用
github.com/spf13/viper
二、读取配置文件
1、yaml文件的书写
port: 8080
cas: "this is my cas"
mysql:
host: "127.0.0.1"
port: "3306"
dbname: "cas"
注:一定要在键值对的:后面加上空格符号
2、配置Viper最少知道在那个路径下寻找需要的配置文件(可以不知道全部路径和其他)
func InitConfig(){
viper.SetConfigName("Conf") //找寻文件的名字
viper.SetConfigType("yaml") // 找寻文件的类型
viper.AddConfigPath("conf") //从当前目录下的哪个文件夹找寻,
viper.AddConfigPath(".") //.代表当前文件夹找寻,可以多个目录找寻,生成数组
err:=viper.ReadInConfig() //读取配置文件
if err!=nil{
if v,ok:=err.(viper.ConfigFileNotFoundError);ok{
fmt.Println(v)
}else{
panic(fmt.Errorf("read config err=%s",err))
}
}
}
func main(){
InitConfig()
cas:=viper.GetString("cas") //Get cas Config
host:=viper.GetString("mysql.host") //Get mysql.host Config
fmt.Println("Get Config")
fmt.Println(cas,host)
}
三、写入配置文件
从配置文件中读取配置文件是有用的,但是有时你想要存储在运行时所做的所有修改。为此,可以使用下面一组命令,每个命令都有自己的用途:
1、WriteConfig - 将当前的viper配置写入预定义的路径并覆盖(如果存在的话)。如果没有预定义的路径,则报错。
2、SafeWriteConfig - 将当前的viper配置写入预定义的路径。如果没有预定义的路径,则报错。如果存在,将不会覆盖当前的配置文件。
3、WriteConfigAs - 将当前的viper配置写入给定的文件路径。将覆盖给定的文件(如果它存在的话)。
4、SafeWriteConfigAs - 将当前的viper配置写入给定的文件路径。不会覆盖给定的文件(如果它存在的话)。
四、监控并重新读取配置文件
viper.WatchConfig()
viper.OnConfigChange(func(in fsnotify.Event) {
//Can Add Some Logics
fmt.Println("Config Was Changed",in.Name)
})
五、从Viper中获取值
Get(key string) : interface{}
GetBool(key string) : bool
GetFloat64(key string) : float64
GetInt(key string) : int
GetIntSlice(key string) : []int
GetString(key string) : string
GetStringMap(key string) : map[string]interface{}
GetStringMapString(key string) : map[string]string
GetStringSlice(key string) : []string
GetTime(key string) : time.Time
GetDuration(key string) : time.Duration
AllSettings() : map[string]interface{}
//判断配置中是否存在这个值
IsSet(key string) : bool
Viper可以通过传入.
分隔的路径来访问嵌套字段
特殊情况:
{
"datastore.metric.host": "0.0.0.0",
"host": {
"address": "localhost",
"port": 5799
},
"datastore": {
"metric": {
"host": "127.0.0.1",
"port": 3099
},
"warehouse": {
"host": "198.0.0.1",
"port": 2112
}
}
}
GetString("datastore.metric.host") // 返回 "0.0.0.0"
六、提取子树
app:
cache1:
max-items: 100
item-size: 64
cache2:
max-items: 200
item-size: 80
让subv赋值给app.cache1
subv := viper.Sub("app.cache1")
subv现在就代表:
max-items: 100
item-size: 64
七、反序列化与序列化
1、根据yaml定制结构体
port: 8080
cas: "this is my cas hhh"
mysql:
host: "127.0.0.1"
port: "3306"
dbname: "cas"
定制的结构体
package models
type Config struct{
Port int `mapstructure:"port"`
Cas string `mapstructure:"cas"`
MySqlConfig `mapstructure:"mysql"`
}
type MySqlConfig struct{
Host string `mapstructure:"host"`
Port int `mapstructure:"port"`
Dbname string `mapstructure:"dbname"`
}
反序列化
err=viper.Unmarshal(&c)
if err!=nil{
panic("Umarshal ERR")
}
也可将Config文件序列化成字符串
import (
yaml "gopkg.in/yaml.v2"
// ...
)
func yamlStringSettings() string {
c := viper.AllSettings()
bs, err := yaml.Marshal(c)
if err != nil {
log.Fatalf("unable to marshal config to YAML: %v", err)
}
return string(bs)
如果看完对自己有所帮助,请点赞支持