我想知道是否有一种方法可以排除cli中用户未设置的标志值。所以我的问题是,我的眼镜蛇cmd
中有一些带有默认值的可选标志。我想知道是否有一种方法可以排除如果用户未设置这些可选标志的情况?或者从另一个角度来看,是否有一种方法可以从cmd
标志集中从cli中提取用户明确更改的标志?
这是一个更好地说明我的情况的例子:
var cmd = &cobra.Command{
Use: "command [operations]",
Short: "Perform some commands",
Run: func(cmd *cobra.Command, args []string) {
var user User
err := viper.Unmarshal(&user)
fmt.Println(err)
fmt.Println(user)
},
}
cmd.PersistentFlags().String("name", "", "Your Name (Required)")
cmd.PersistentFlags().String("description", "", "Description")
cmd.PersistentFlags().String("address", "", "Address")
cmd.PersistentFlags().Int("age", -1, "Age")
cmd.MarkPersistentFlagRequired("name")
viper.BindPFlags(cmd.PersistentFlags())
所以假设年龄和地址,我希望它们是可选的,并且在传递给struct时不要传播。因此,这意味着在cli中,不需要用户提交age
和address
标志,并且这些可选标志的默认值为nil。但是,Int&String标志是强类型的,因此它们需要默认值(例如:""
和-1
)。结果,当我将命令pflag绑定到viper且用户未在cli中输入年龄和地址值时,viper将收到""
作为地址,-1
作为年龄。使用上述方法,默认值将传播到User结构。
我想要的是排除用户未设置的标志值。我有什么办法可以将User结构排除在用户未明确设置的标志值之外?
我当前在User结构中排除未设置标志的当前解决方案是这样的:
map[string]interface{}
flags.Changed("flag")
设置/更改了标志。如果标志已更改,则将其添加到地图解组json对象以构造
// inside the Run function of a cobra command
aMap := make(map[string]interface{})
flags := cmd.Flags()
for _, flag := range cmdFlags {
if flags.Changed(flag) {
aMap[flag] = viper.Get(flag)
}
}
jsonStr, _ := json.Marshal(aMap)
var user User
json.Unmarshal(jsonStr, &user)
fmt.Println(user)
但是我想知道是否有比我上面的解决方案更好的选择。最好是,我不想更改User
结构中的任何内容,因为它是从外部包中导入的。
谢谢。非常感谢您的帮助。
答案 0 :(得分:0)
假设您的User
结构看起来像这样:
type User struct {
...
age int
address string
...
}
然后默认情况下,User
结构的初始化将设置age => 0, address => 0
。因此,即使viper没有设置默认值。内部去吧。
我的建议是:
1.更改用户结构的创建方式
type User struct {
...
age *int
address *string
...
}
nil
。nil
值。希望有帮助!