【问题标题】:Can I add commands with Go flags?我可以添加带有 Go 标志的命令吗?
【发布时间】:2017-01-11 19:32:56
【问题描述】:

我知道我可以这样定义标志:

initPtr := flag.String("init", "config.json", "Initialize with config filename")

我会这样称呼:

myapp --init=myconfig.json

我想知道我是否可以定义类似命令的东西,以便像这样调用应用程序?

myapp init --filename=myconfig.json
myapp check --filename=myconfig.json
myapp run

【问题讨论】:

    标签: go config


    【解决方案1】:

    您可以结合使用command line arguments 和flags。

    例如。

    configFilePtr := flag.String("filename", "", "Config Filename")
    flag.Parse()
    
    n := len(os.Args)
    if n > 1 {
        switch os.Args[1] {
            case "init":
                initApp(*configFilePtr)
            case "check":
                checkApp(*configFilePtr)
            case "run":
                runApp()
        }
    }
    

    另一种选择是使用 spf13's cobra 之类的东西。

    更新:

    如果您需要根据命令使用不同的标志,您可以使用FlagSet,如Kare Nuorteva 的答案中所述。

    例如。

    f1 := flag.NewFlagSet("f1", flag.ContinueOnError)
    silent := f1.Bool("silent", false, "")
    f2 := flag.NewFlagSet("f2", flag.ContinueOnError)
    loud := f2.Bool("loud", false, "")
    
    switch os.Args[1] {
      case "apply":
        if err := f1.Parse(os.Args[2:]); err == nil {
          fmt.Println("apply", *silent)
        }
      case "reset":
        if err := f2.Parse(os.Args[2:]); err == nil {
          fmt.Println("reset", *loud)
        }
    }
    

    Reference

    【讨论】:

    • 请注意,您无法覆盖保留的标志。如果我记得,“构建”和“帮助”就是两个这样的标志。 “运行”可能是另一个。
    【解决方案2】:

    是的,你可以。

    查看 https://golang.org/pkg/flag/ 获取 FlagSet 文档。

    还有一个工作示例:https://github.com/constabulary/gb/blob/master/cmd/gb/main.go

    还有一个 miltonb 要求的示例:

    % go run flagset.go init --filename=foo.json foo bar
    init foo.json [foo bar]
    % go run flagset.go check --filename=bar.json 1 2 3
    check bar.json [1 2 3]
    % go run flagset.go run
    run
    % cat flagset.go
    package main
    
    import (
        "flag"
        "fmt"
        "os"
    )
    
    func main() {
        init := flag.NewFlagSet("init", flag.ExitOnError)
        initFile := init.String("filename", "myconfig.json", "configuration file")
    
        check := flag.NewFlagSet("check", flag.ExitOnError)
        checkFile := check.String("filename", "myconfig.json", "configuration file")
    
        if len(os.Args) <= 1 {
            flag.Usage()
            os.Exit(1)
        }
    
        switch os.Args[1] {
        case "init":
            if err := init.Parse(os.Args[2:]); err == nil {
                fmt.Println("init", *initFile, init.Args())
            }
        case "check":
            if err := check.Parse(os.Args[2:]); err == nil {
                fmt.Println("check", *checkFile, check.Args())
            }
        case "run":
            fmt.Println("run")
        }
    }
    

    【讨论】:

    • 如果您添加一个关于实现工作原理的小示例,那将非常酷。
    猜你喜欢
    • 2015-10-25
    • 1970-01-01
    • 1970-01-01
    • 2014-04-09
    • 2012-07-21
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多