/ 前言 /
viper是由Steve Francia编写的开源配置解决方案, 也是cobra的作者, 我们来看下viper的功能
- 支持JSON、TOML、YAML/YML、PROPERTIES、ENVFILE等文件的读取
- 修改读取文件的键值数据
- 监听配置文件的修改并自动重新加载
下载
go get github.com/spf13/viper
/ 1 / 读取配置文件
在读取配置文件中我们将会演示viper
的集中使用方式
我们以.yml
文件为例
config.yml
user:
name: "wise"
age: 18
config.go
package config
import (
"fmt"
"github.com/spf13/viper"
)
// 这里的配置文件读取可以使用相对路径, 我这里因为是同级所以直接使用config.yml即可
//var filePath = "../test/config.yml"
var filePath = "config.yml"
var cfg = Config{}
// 这里有俩种写法, 如果你要读取的配置文件比较大而且类型较多那么建议你使用第二种
// 第一种
type Config struct {
UserInfo struct{
Name string `mapstructure:"name"`
Age string `mapstructure:"age"`
} `mapstructure:"user"`
}
// 第二种
type Config struct {
User UserInfo `mapstructure:"user"`
}
UserInfo struct{
Name string `mapstructure:"name"`
Age int `mapstructure:"age"`
}
func LoadConfig() {
// 设置配置文件信息
viper.SetConfigType("yml")
viper.SetConfigFile(filePath)
// 读取配置文件
err := viper.ReadInConfig()
if err != nil {
fmt.Println("读取配置文件失败, 异常信息 : ", err)
}
// 直接从viper对象中获取key的value数据,并且可以定义类型
fmt.Println(viper.Get("user.name"))
fmt.Println(viper.GetInt("user.age"))
// 判断key是否存在, 返回true/false
fmt.Println(viper.IsSet("user.name"))
// 设置key的value值, 优先级最高, 可以在读取配置文件之前设置
viper.Set("user.age",19)
// 将文件内容解析后封装到cfg对象中
err = viper.Unmarshal(&cfg)
if err != nil {
fmt.Println("解析配置文件失败, 异常信息 : ", err)
}
}
// 使用时直接调用该方法即可
func GetInfo() Config {
return cfg
}
测试代码
config_test.go
import (
"fmt"
"testing"
)
func TestGetInfo(t *testing.T) {
LoadConfig()
fmt.Println("name : ",GetInfo().UserInfo.Name)
fmt.Println("age : ",GetInfo().UserInfo.Age)
}
输出信息
name : wise
age : 18
我们总结一下在上面我们使用到的viper的功能
- 可以在直接从
viper
对象中获取数据 - 直接从
viper
对象中获取数据时可以指定返回类型 - 可以在读取配置文件之前修改
value
的值, 且优先级最高
/ 2 / 自动更新配置文件
我们来看一下viper
是否可以自动更新配置文件
package main
import (
"fmt"
"github.com/spf13/viper"
"time"
)
func main() {
viper.SetConfigType("yml")
viper.SetConfigFile("./test/config.yml")
err := viper.ReadInConfig()
if err != nil {
fmt.Println("read config is failed err:", err)
}
viper.WatchConfig()
fmt.Println("age : ", viper.GetInt("user.age"))
// 我们让线程睡眠20s, 在此期间我们去修改config.yml文件中age的值
time.Sleep(time.Second * 20)
fmt.Println("age : ", viper.GetInt("user.age"))
}
输出信息
age : 18
age : 180
俩次打印结果一样的朋友可以将睡眠时间调整的再长一点试一下