1. 構(gòu)建Go命令行程序工具鏈

        共 4447字,需瀏覽 9分鐘

         ·

        2022-06-27 23:08

        偷懶的故事

        今天的推薦需要從一個偷懶的故事說起···

        話說不久前,需要輸出一個按發(fā)布時間排序的酷Go推薦的歷史文章列表,類似于這樣:

        于是乎,想著從GoCN上一篇一篇copy文章的標(biāo)題吧,5篇下來,手眼已經(jīng)不協(xié)調(diào)了,此時此刻才想起自己貌似是個碼農(nóng),此情此景那必須coding一段,讓代碼來輸出這個列表。

        思路很簡單,看一下GoCN文章列表的API,再看下鑒權(quán)方式(看header是通過cookie),然后就可以coding了,通過API拉取文章數(shù)據(jù),提取需要的字段再組裝成MD輸出就完事了!

        當(dāng)準(zhǔn)備一個main.go搞定的時候,本著對coding的敬畏,簡單的思考了一下程序的可讀性、拓展性,決定還是構(gòu)建一個比較完整的命令行程序,如下:

        主角登場

        那么要實現(xiàn)上圖的命令行提示,程序參數(shù)解析等,不借助于第三方包當(dāng)然也能實現(xiàn)。但,前人種好的大樹為哈不乘涼呢,在業(yè)界對于命令行工具的開發(fā)已經(jīng)有比較成熟的實現(xiàn),下面清楚本文的主角:

        • cobra:應(yīng)用命令行框架
        • pflag:命令行參數(shù)解析
        • viper:配置文件解析
        下面結(jié)合實際項目來看如何使用這三位大哥來構(gòu)建Go命令行程序。

        先簡單看下項目結(jié)構(gòu):

        .
        ├── cmd
        │   ├── pull.go
        │   └── root.go
        ├── config.yaml
        ├── file
        │   └── cool-go.md
        ├── go.mod
        ├── go.sum
        ├── gocn-cli
        └── main.go

        然后引入上面所推薦的三個庫:

        go get -u github.com/spf13/cobra@latest

        go get -u github.com/spf13/viper

        go get -u github.com/spf13/pflag

        Coding

        package cmd

        import (
            "fmt"
            "github.com/spf13/cobra"
            "github.com/spf13/viper"
            "os"
        )

        var (
            cfgFile string
        )

        func init() {
            cobra.OnInitialize(initConfig)
            
            // 解析配置文件參數(shù)
            rootCmd.PersistentFlags().StringVar(&cfgFile, "config""""config file (default is ./config.yaml)")
        }

        // initConfig viper加載配置文件
        func initConfig() {
            if cfgFile != "" {
                viper.SetConfigFile(cfgFile)
            } else {
                viper.AddConfigPath(".")
                viper.SetConfigName("config")
            }
            
            if err := viper.ReadInConfig(); err != nil {
                fmt.Println("Can't read config file:", err)
                os.Exit(1)
            }
        }

        // 創(chuàng)建全局rootCmd
        var rootCmd = &cobra.Command{
            Use:   "gocn-cli",
            Short: "gocn-cli is a command line tool for gocn.com",
            Long:  "gocn-cli is a command line tool for gocn.com",
            Run: func(cmd *cobra.Command, args []string) {
                
            },
        }

        // Execute 執(zhí)行命令 main調(diào)用
        func Execute() {
            if err := rootCmd.Execute(); err != nil {
                fmt.Println(err)
                os.Exit(1)
            }
        }

        package cmd

        import (
         "github.com/spf13/cobra"
         "github.com/spf13/viper"
         "os"
        )

        var (
         moduleName string
        )

        func init() {
            // 給rootCmd增加新的命令pullCmd
         rootCmd.AddCommand(pullCmd)

         pullCmd.Flags().StringVarP(&moduleName, "module""m""""module name")
        }

        var pullCmd = &cobra.Command{
         Use:   "pull gocn data",
         Short: "pull gocn data",
         Run: func(cmd *cobra.Command, args []string) {
          pullHandler()
         },
        }

        // pullHandler pullCmd 對應(yīng)的處理函數(shù)
        func pullHandler() {
         if moduleName == "" {
          fmt.Println("module name is required")
          os.Exit(1)
         }

         switch moduleName {
         case "cool-go":
          pullCoolGo()

         default:
          fmt.Println("module name is invalid")
          os.Exit(1)
         }
        }

        func pullCoolGo() {
         // TODO Write Your Code
        }

        結(jié)語

        以上簡單介紹了如何使用cobra、viper、pflag,當(dāng)然它們的用法還有很多,這里只做個簡單的入門。
        可見,通過簡單的代就能構(gòu)建出比較好的命令行程序。

        參考

        • https://github.com/spf13/cobra
        • https://github.com/spf13/viper
        • https://github.com/spf13/pflag


        往期推薦



        等等,怎么使用 SetMemoryLimit?


        第八屆 GopherChina 大會蓄勢待發(fā)!


        這不會又是一個Go的BUG吧?

        想要了解Go更多內(nèi)容,歡迎掃描下方?? 關(guān)注 公眾號,回復(fù)關(guān)鍵詞 [實戰(zhàn)群]  ,就有機(jī)會進(jìn)群和我們進(jìn)行交流

        分享、在看與點贊,至少我要擁有一個叭~

        瀏覽 62
        點贊
        評論
        收藏
        分享

        手機(jī)掃一掃分享

        分享
        舉報
        評論
        圖片
        表情
        推薦
        點贊
        評論
        收藏
        分享

        手機(jī)掃一掃分享

        分享
        舉報
          
          

            1. 极品97尤物被啪到呻吟喷水 | 北条麻纪久久播放视频 | 国产美女**毛片1 | 久久久久久久久亚洲精品壹牛 | 日本wwwwxxxx泡妞下课 |