概要
今年も大量のツールのようなものを作った.Golangで実装する場合にはkubectlやfaas-cli を参考にパクるとなんとなくいい感じのツールが作れます.
packageの紹介
spf13/cobra
フラグ処理やサブコマンド,ヘルプメッセージ,インテリジェントな提案,アプリケーション用に自動的に生成されたbashオートコンプリートなど,CLI ツールに必要なことはカバーできてしまいます.
kubectlやfaas-cli にも実際に使われています.
Cobraの構造の理想は以下のような実装です.
▾ appName/ ▾ cmd/ add.go your.go commands.go here.go main.go
一つのファイルにまとめてしまうこともできます. Fizzbuzz をサンプルに追加したもの以下です.
package main import ( "fmt" "github.com/spf13/cobra" "strconv" "strings" ) func fizzbuzz(max int) { for i := 0; i <= max; i++ { fizz := i%3 == 0 buzz := i%5 == 0 switch { case fizz && buzz: fmt.Println("fizzbuzz") case fizz && !buzz: fmt.Println("fizz") case !fizz && buzz: fmt.Println("buzz") default: fmt.Println(i) } } } func main() { var echoTimes int var cmdPrint = &cobra.Command{ Use: "print [string to print]", Short: "Print anything to the screen", Long: `print is for printing anything back to the screen. For many years people have printed back to the screen.`, Args: cobra.MinimumNArgs(1), Run: func(cmd *cobra.Command, args []string) { fmt.Println("Print: " + strings.Join(args, " ")) }, } var cmdEcho = &cobra.Command{ Use: "echo [string to echo]", Short: "Echo anything to the screen", Long: `echo is for echoing anything back. Echo works a lot like print, except it has a child command.`, Args: cobra.MinimumNArgs(1), Run: func(cmd *cobra.Command, args []string) { fmt.Println("Print: " + strings.Join(args, " ")) }, } var cmdTimes = &cobra.Command{ Use: "times [# times] [string to echo]", Short: "Echo anything to the screen more times", Long: `echo things multiple times back to the user by providing a count and a string.`, Args: cobra.MinimumNArgs(1), Run: func(cmd *cobra.Command, args []string) { for i := 0; i < echoTimes; i++ { fmt.Println("Echo: " + strings.Join(args, " ")) } }, } var cmdFizbuzz = &cobra.Command{ Use: "fizzbuzz [int]", Short: "return Fizzbuzz", Long: `echo things multiple times back to the user by providing a count and a string.`, Args: cobra.MinimumNArgs(1), Run: func(cmd *cobra.Command, args []string) { var m int m, _ = strconv.Atoi(args[0]) fizzbuzz(m) }, } cmdTimes.Flags().IntVarP(&echoTimes, "times", "t", 1, "times to echo the input") var rootCmd = &cobra.Command{Use: "app"} rootCmd.AddCommand(cmdPrint, cmdEcho, cmdFizbuzz) cmdEcho.AddCommand(cmdTimes) rootCmd.Execute() }
使ってみる
$ ./appName -help Error: unknown shorthand flag: 'e' in -elp Usage: app [command] Available Commands: echo Echo anything to the screen fizzbuzz return Fizzbuzz help Help about any command print Print anything to the screen $ ./appName fizzbuzz 15 fizzbuzz 1 2 fizz 4 buzz fizz 7 8 fizz buzz 11 fizz 13 14 fizzbuzz
spf13/viper
yaml, toml などの設定ファイル・環境変数・フラグなどの設定値を透過的に扱えるようにするライブラリ. めちゃくちゃに便利
spf13/pflag
置き換え実装 cobraの中身はこれ
morikuni/aec
出力に色を付ける.
最後に
私がCLIツールを作るときはCobraに全面的に従うことが多いのですし困ったことはありません. もしかしたらもっと素晴らしい方法があるかもしれませんが....