命令行界面(Command-line Interfaces)是比较常用的一种软件形式。对于大部分开发运维人员来说很多时候CLIs可能比图形界面更加方便。软件开发时也经常会有需要开发命令行界面形式软件的情况,使用Golang来开发是一种比较不错的选择。这篇文章将简单介绍使用Golang标准库中os.Args和flag包编写命令行界面。
os.Argsosvar Args []stringos.Args[0]
Args hold the command-line arguments, starting with the program name.
flagos.Args[1:]
flag
app -arg1 --arg2 -arg3=val -arg4 valflag
flag-flag value--flag value-flag--flag
func Type(name string, value Type, usage string) *TypenamevalueusageType
func Parse()
-flag--flag-flag=value--flag=value-flag value--flag value=
123406640x1234-1-2551tTtrueTRUETrue0fFfalseFALSEFalse
flagfunc TypeVar(p *Type, name string, value Type, usage string)
flag-h--h-help--help
这个帮助选项输出的信息也可以自定义:
func NArg() intfunc Arg(i int) stringfunc Args() []string
到目前为止虽然只是在将命令行参数获取和解析等内容,但这就是编写命令行界面程序最核心的部分了,剩下的无法是根据解析得到的内容进行相应的处理。
FlagSetflagFlagSet
package mainimport ("flag""fmt""os"
)func fncmda() {cmda := flag.NewFlagSet("cmda", flag.ContinueOnError) // 创建子命令解析器sFlag := cmda.String("s", "naisu", "help msg for cmda -s") // 设置子命令选项err := cmda.Parse(os.Args[2:]) // 从下标2的参数开始解析if err != nil {fmt.Println(err)}fmt.Println(*sFlag)
}func fncmdb() {cmdb := flag.NewFlagSet("cmdb", flag.ContinueOnError) // 创建子命令解析器iFlag := cmdb.Int("i", 233, "help msg for cmdb -i") // 设置子命令选项err := cmdb.Parse(os.Args[2:]) // 从下标2的参数开始解析if err != nil {fmt.Println(err)}fmt.Println(*iFlag)
}func main() {if len(os.Args) < 2 {os.Args = append(os.Args, "default")}switch os.Args[1] { // 根据不同子命令进行不同处理case "cmda":fncmda()case "cmdb":fncmdb()default:fmt.Println("子命令不存在")}
}
使用这些方式可以实现更加个性化或更加复杂的设置,但是通常不推荐怎么做,如果有更多的需求,更加推荐使用线程的框架来处理。
总结对于简单的项目使用上面方式开发使用还是挺方便的。对于复杂的项目或是功能更加完善的项目来说使用现有的框架来开发会更加方便。Golang中用来开发命令行界面的框架比较热门的有下面两个:
- Cobra
https://cobra.dev/
https://github.com/spf13/cobra - urfave/cli
https://cli.urfave.org/
https://github.com/urfave/cli