英文:
How to combine cobra and klog
问题
我有一个项目需要使用cobra
和klog
来生成可执行文件并打印日志并保存。
首先,我测试了使用以下的klog
可以同时将日志输出到终端和文件
。
package main
import (
"flag"
"k8s.io/klog"
)
func init() {
var fs flag.FlagSet
klog.InitFlags(&fs)
fs.Set("logtostderr", "false")
fs.Set("log_file_max_size", "100")
fs.Set("log_file", "/home/test/workspace/klogfile/test.log")
fs.Set("alsologtostderr", "true")
}
func main() {
defer klog.Flush()
klog.Info("info")
klog.Warning("warning")
klog.Error("error")
}
文件/home/test/workspace/klogfile/test.log
的内容如下:
Log file created at: 2023/04/06 16:46:07
Running on machine: s52
Binary: Built with gc go1.16.12 for linux/amd64
Log line format: [IWEF]mmdd hh:mm:ss.uuuuuu threadid file:line] msg
I0406 16:46:07.751183 13512 main.go:20] info
W0406 16:46:07.751594 13512 main.go:21] warning
E0406 16:46:07.751629 13512 main.go:22] error
然后我尝试基于k8s
风格将其添加到cobra
中:
package main
import (
"flag"
"github.com/spf13/cobra"
"k8s.io/klog"
)
var (
str = "hello world"
)
func NewCommand() *cobra.Command {
cmd := &cobra.Command{
Use: "echo",
Short: "use klog with cobra",
Long: "Use klog together with cobra.",
Run: func(cmd *cobra.Command, args []string) {
Run()
},
}
klog.InitFlags(flag.CommandLine)
cmd.Flags().AddGoFlagSet(flag.CommandLine)
cmd.Flags().SortFlags = false
cmd.Flags().StringVar(&str, "str", str, "string to print")
return cmd
}
func Run() {
defer klog.Flush()
klog.Infof("Running, str:%s", str)
}
func main() {
if err := NewCommand().Execute(); err != nil {
klog.Fatalf("root cmd execute failed, err=%v", err)
}
}
我可以通过--help
打印出所需的日志选项
,但是当我覆盖它们以实现上面示例中的保存到文件时,只有输出被输出到终端而不是文件。
# go run main2.go --logtostderr false --log_file_max_size "100" --alsologtostderr true --log_file "/home/test/workspace/klogfile/test2.log"
I0406 16:52:57.479455 15217 cobra_klog.go:34] Running, str:hello world
请问我在哪里缺少必要的代码
,如果是的话,请告诉我如何修改,谢谢!
英文:
I have a project that needs to use cobra
and klog
to generate executable and print logs and keep.
Firstly, I tested that using the following klog
can output the log to the terminal and file
at the same time.
package main
import (
"flag"
"k8s.io/klog"
)
func init() {
var fs flag.FlagSet
klog.InitFlags(&fs)
fs.Set("logtostderr", "false")
fs.Set("log_file_max_size", "100")
fs.Set("log_file", "/home/test/workspace/klogfile/test.log")
fs.Set("alsologtostderr", "true")
}
func main() {
defer klog.Flush()
klog.Info("info")
klog.Warning("warning")
klog.Error("error")
}
The content of file /home/test/workspace/klogfile/test.log
is as follow
Log file created at: 2023/04/06 16:46:07
Running on machine: s52
Binary: Built with gc go1.16.12 for linux/amd64
Log line format: [IWEF]mmdd hh:mm:ss.uuuuuu threadid file:line] msg
I0406 16:46:07.751183 13512 main.go:20] info
W0406 16:46:07.751594 13512 main.go:21] warning
E0406 16:46:07.751629 13512 main.go:22] error
Then I try to add it to cobra
based on k8s style
package main
import (
"flag"
"github.com/spf13/cobra"
"k8s.io/klog"
)
var (
str = "hello world"
)
func NewCommand() *cobra.Command {
cmd := &cobra.Command{
Use: "echo",
Short: "use klog with cobra",
Long: "Use klog together with cobra.",
Run: func(cmd *cobra.Command, args []string) {
Run()
},
}
klog.InitFlags(flag.CommandLine)
cmd.Flags().AddGoFlagSet(flag.CommandLine)
cmd.Flags().SortFlags = false
cmd.Flags().StringVar(&str, "str", str, "string to print")
return cmd
}
func Run() {
defer klog.Flush()
klog.Infof("Running, str:%s", str)
}
func main() {
if err := NewCommand().Execute(); err != nil {
klog.Fatalf("root cmd execute failed, err=%v", err)
}
}
I can print out the required log options
through --help
, but when I override them to achieve the save to file in the above example, only the output is output to the terminal and not to the file
# go run main2.go --logtostderr false --log_file_max_size "100" --alsologtostderr true --log_file "/home/test/workspace/klogfile/test2.log"
I0406 16:52:57.479455 15217 cobra_klog.go:34] Running, str:hello world
May I ask where I am missing the necessary code
, if so, please let me know how to modify it, thank you!
答案1
得分: 1
你的代码没有问题。唯一的问题是你必须使用-flag=false
的形式来关闭布尔标志(参见命令行标志语法)。
尝试使用以下命令(将--logtostderr false
替换为--logtostderr=false
):
go run main2.go --logtostderr=false --log_file_max_size "100" --alsologtostderr=true --log_file "/home/test/workspace/klogfile/test2.log"
顺便说一下,我认为--log_file_max_size "100"
可以简化为--log_file_max_size 100
。
更新:
为了减少klog的暴露标志:
package main
import (
"flag"
"github.com/spf13/cobra"
"k8s.io/klog"
)
var (
str = "hello world"
+ logFile string
)
func NewCommand() *cobra.Command {
+ var fs flag.FlagSet
+ klog.InitFlags(&fs)
cmd := &cobra.Command{
Use: "echo",
Short: "use klog with cobra",
Long: "Use klog together with cobra.",
Run: func(cmd *cobra.Command, args []string) {
+ fs.Set("logtostderr", "false")
+ fs.Set("log_file", logFile)
Run()
},
}
- klog.InitFlags(flag.CommandLine)
- cmd.Flags().AddGoFlagSet(flag.CommandLine)
cmd.Flags().SortFlags = false
cmd.Flags().StringVar(&str, "str", str, "string to print")
+ cmd.Flags().StringVar(&logFile, "log_file", "", "If non-empty, use this log file")
return cmd
}
func Run() {
defer klog.Flush()
klog.Infof("Running, str:%s", str)
}
func main() {
if err := NewCommand().Execute(); err != nil {
klog.Fatalf("root cmd execute failed, err=%v", err)
}
}
希望对你有帮助!
英文:
There is nothing wrong in your code. The only issue is that you must use the -flag=false
form to turn off a boolean flag (see Command line flag syntax).
Try this command (repalce --logtostderr false
with --logtostderr=false
):
go run main2.go --logtostderr=false --log_file_max_size "100" --alsologtostderr true --log_file "/home/test/workspace/klogfile/test2.log"
BTW, I think --log_file_max_size "100"
could be simplified to --log_file_max_size 100
.
Update:
To reduce the exposed flags of klog:
package main
import (
"flag"
"github.com/spf13/cobra"
"k8s.io/klog"
)
var (
str = "hello world"
+ logFile string
)
func NewCommand() *cobra.Command {
+ var fs flag.FlagSet
+ klog.InitFlags(&fs)
cmd := &cobra.Command{
Use: "echo",
Short: "use klog with cobra",
Long: "Use klog together with cobra.",
Run: func(cmd *cobra.Command, args []string) {
+ fs.Set("logtostderr", "false")
+ fs.Set("log_file", logFile)
Run()
},
}
- klog.InitFlags(flag.CommandLine)
- cmd.Flags().AddGoFlagSet(flag.CommandLine)
cmd.Flags().SortFlags = false
cmd.Flags().StringVar(&str, "str", str, "string to print")
+ cmd.Flags().StringVar(&logFile, "log_file", "", "If non-empty, use this log file")
return cmd
}
func Run() {
defer klog.Flush()
klog.Infof("Running, str:%s", str)
}
func main() {
if err := NewCommand().Execute(); err != nil {
klog.Fatalf("root cmd execute failed, err=%v", err)
}
}
通过集体智慧和协作来改善编程学习和解决问题的方式。致力于成为全球开发者共同参与的知识库,让每个人都能够通过互相帮助和分享经验来进步。
评论