List 在Go中解组Yaml时,如何设置列表中键的默认值?
我有一个类似下面的YAMLList 在Go中解组Yaml时,如何设置列表中键的默认值?,list,go,yaml,default,List,Go,Yaml,Default,我有一个类似下面的YAML connections: - name: demo hosts: - demo.example.com:9200 username: admin password: password ssl: true ssl_verify: true version: 7 - name: test hosts: - "test.example.com:9200" username: ad
connections:
- name: demo
hosts:
- demo.example.com:9200
username: admin
password: password
ssl: true
ssl_verify: true
version: 7
- name: test
hosts:
- "test.example.com:9200"
username: admin
password: password
如您所见,ssl
和ssl\u验证
未设置在列表的第二项中。我希望它们在默认情况下为true
,但是,它不会发生。我尝试了不同的解决方案
false
初始化,我们无法确定用户是否输入了false
nil
,并且易于捕获。但是,在使用config struct时需要取消对指针的引用,这不是很方便。或者,可以基于解组生成的结构生成新结构有什么想法吗?您可以使用一个函数来完成这项工作:
type Connection struct {
Name string
Hosts []string
Username string
Password string
Ssl *bool
SslVerify bool
Version int
}
// If Ssl is nil, returns true
// otherwise the value
func (c Connection) IsSSL() bool {
return c.Ssl == nil || *c.Ssl
}
type Config struct {
Connections []Connection
}
编辑
或者,更好的是,简单地颠倒你的布尔逻辑:
type Connection struct {
Name string
Hosts []string
Username string
Password string
SkipSsl bool
SkipSslVerify bool
Version int
}
通过这种方式,除非在配置中明确指出不同,否则将使用SSL,这在有人阅读配置时会非常突出。我明白了。我正在
unmarshalyml
回调中使用github.com/creasty/defaults
type Config struct {
Connections []Connection
}
type Connection struct {
Name string
Hosts []string
Username string
Password string
Ssl bool `default:"true"`
SslVerify bool `default:"true" yaml:"ssl_verify"`
Version int `version:"7"`
}
func (s *Connection) UnmarshalYAML(unmarshal func(interface{}) error) error {
defaults.Set(s)
type plain Connection
if err := unmarshal((*plain)(s)); err != nil {
return err
}
return nil
}
此外,此解决方案还可用于验证目的。您是否尝试过
viper.SetDefault(“connections.ssl”,true)
?ie没有[]
并传入实际的布尔值而不是字符串。是的,它不起作用。它只在连接不是数组的情况下对结构有效,但这不是我所需要的。问题似乎是,在解组之前,你不知道连接集合中有多少元素,所以没有一个好方法用默认值初始化切片。您是否可以控制Config
struct本身的定义?在这种情况下,将属性重命名为NoSsl
和nosslvify
可能是重新设置框架的好方法。您可以先将其作为哈希映射加载,填充间隙,转储(到文件或字符串),然后使用适当的类型重新加载。这样,您就不必在运行时的其余部分进行检查。键入简单连接
,这很好。这应该包括在godoc中的解组halyaml(目前不存在)示例中。
type Connection struct {
Name string
Hosts []string
Username string
Password string
Ssl *bool
SslVerify bool
Version int
}
// If Ssl is nil, returns true
// otherwise the value
func (c Connection) IsSSL() bool {
return c.Ssl == nil || *c.Ssl
}
type Config struct {
Connections []Connection
}
type Connection struct {
Name string
Hosts []string
Username string
Password string
SkipSsl bool
SkipSslVerify bool
Version int
}
type Config struct {
Connections []Connection
}
type Connection struct {
Name string
Hosts []string
Username string
Password string
Ssl bool `default:"true"`
SslVerify bool `default:"true" yaml:"ssl_verify"`
Version int `version:"7"`
}
func (s *Connection) UnmarshalYAML(unmarshal func(interface{}) error) error {
defaults.Set(s)
type plain Connection
if err := unmarshal((*plain)(s)); err != nil {
return err
}
return nil
}