Go语言 命令行解析(二)
今天我們繼續講解Go語言中命令行,當我們在解析命令行傳遞的參數時通常會想用最簡單的方法來解析自己行用到的命令行參數,那么urfave/cli可以幫助我們快速的解析命令行參數,它是一個簡單快速的命令行包,用于在Go語言中構建命令行應用程序,目的是使開發人員能夠以表達的方式編寫快速分發的命令行應用程序,urfave/cli庫抽象出來:Flag、Command,SubCommand等模塊,用戶只需要設置模塊信息,參數的解析和關聯就可以,幫助信息自動生成。
在C語言中可以通過getopt(int argc, char * const argv[], const char *optstring)來完成參數解析,這里不做示例,有興趣的同學可以自己動手嘗試一下。
安裝urfave/cli:
go get github.com/urfave/cli包引用方法:
import "github.com/urfave/cli" //引入cli包urfave/cli包中幾個重要的方法:
cli.NewApp() // 創建一個cli實例 Run() // 程序入口,執行Run后分析參數切片和路由 app.Commands // 要執行的命令列表 app.Before // 運行命令之前執行的內容 app.After // 運行命令之后執行的內容 Subcommands // 子命令好,開始我們演示,今天的演示示例有點長,項目目錄結構如下:
#tree . |-- commands | |-- api | | `-- api.go // api commands | `-- service | `-- service.go // 服務 commands |-- go_cli.go // main入口 |-- go.mod // go module管理包 |-- go.sum `-- webservice|-- bin| `-- webservice`-- webservice.go // web服務類首先,定義webservice類:
webservice類主要完成幾個功能:構造函數,釋放資源函數,ApiService方法和Service方法。
package webserviceimport "fmt"// web service 類 type WebService struct {Config stringPort intLogFile string }// 返回web service 實例 func NewWebService(config, logFile string, port int) *WebService {var ws = &WebService{Port: port,Config: config,LogFile: logFile,}return ws }// 釋放資源 func (ws *WebService) Freed() {}// API調用啟動方式 func (ws *WebService) ApiService() {fmt.Println("api service")fmt.Printf("port : %d \n", ws.Port)fmt.Printf("config : %s \n", ws.Config)fmt.Printf("logfile : %s \n", ws.LogFile)// 啟動http服務 }// 常駐方式啟動 func (ws *WebService) Service() {fmt.Println("service")fmt.Printf("config : %s \n", ws.Config)fmt.Printf("logfile : %s \n", ws.LogFile)// 可以理解成類似Nginx這類服務的啟動 }我們創建Api和Service兩個Commands的目錄,用于分開執行HTTPService和Service兩種模式。
ApiService:
在日常工作中,HTTP-Api是比較常見的獲取數據的方式,我們用這個例子來看看在命令行里面如何啟動和傳遞參數的。
package apiimport ("fmt""github.com/gzh/webservice""github.com/urfave/cli""os" )var Command = cli.Command{Name: "api",Aliases: []string{"web_api", "webApi"}, // 命令別名Flags: []cli.Flag{// int型參數port,value默認是8080cli.IntFlag{Name: "port",Value: 8080,Usage: "/usr/local/web_service/service api --port=8080",},// 字符型參數配置文件,默認值為空cli.StringFlag{Name: "config",Value: "",Usage: "/usr/local/web_service/service api --config=/usr/local/web_service/config",},// 字符型日志文件參數,默認值為空cli.StringFlag{Name: "log_file",Value: "",Usage: "/usr/local/web_service/service api --log_file=/usr/local/web_service/log/web_service.log",},},Action: func(c *cli.Context) error {var port = c.Int("port") // 從上下文中獲取端口var config = c.String("config") // 從上下文中獲取配置文件var logFile = c.String("log_file") // 從上下文中獲取日志文件if config == "" {_, _ = fmt.Fprintf(os.Stderr, "config is empty!\n")os.Exit(100001) // 配置文件錯誤碼}if port <= 0 {_, _ = fmt.Fprintf(os.Stderr, "port is empty!\n")os.Exit(100002) // 端口錯誤碼}if logFile == "" {_, _ = fmt.Fprintf(os.Stderr, "log_file is empty!\n")os.Exit(100003) // 日志文件錯誤碼}// 實例webservice,構造函數參數:config,logfile,portvar api = webservice.NewWebService(config, logFile, port)defer api.Freed()// 啟動HTTP-API服務api.ApiService()return nil}, }Service:
Service類似于Nginx一樣,啟動后常駐執行的服務,這種在后端中比較多見,下面的示例為Service的啟動和傳遞參數方式。
package serviceimport ("fmt""github.com/gzh/webservice""github.com/urfave/cli""os" )var Command = cli.Command{Name: "service",Flags: []cli.Flag{// 字符型參數配置,默認值為空cli.StringFlag{Name: "config",Value: "",Usage: "/usr/local/web_service/service api --config=/usr/local/web_service/config",},// 字符型日志文件參數,默認值為空cli.StringFlag{Name: "log_file",Value: "",Usage: "/usr/local/web_service/service api --log_file=/usr/local/web_service/log/web_service.log",},},Action: func(c *cli.Context) error {var config = c.String("config") // 從上下文中獲取配置文件var logFile = c.String("log_file") // 從上下文中獲取日志文件if config == "" {_, _ = fmt.Fprintf(os.Stderr, "config is empty!\n")os.Exit(100001) // 配置文件錯誤碼}if logFile == "" {_, _ = fmt.Fprintf(os.Stderr, "log_file is empty!\n")os.Exit(100003) // 日志文件錯誤碼}// 實例webservice,構造函數參數:config,logfilevar api = webservice.NewWebService(config, logFile, 0)defer api.Freed()// 啟動服務api.Service()return nil}, }完成上面的幾個類之后,我們可以創建go_cli.go文件開始我們的編碼。主要是實現main函數,里面創建cli實例,配置參數解析相關信息、版本、描述和幫助等信息。
package mainimport ("fmt""github.com/gzh/commands/api""github.com/gzh/commands/service""github.com/urfave/cli""os" )func main() {// 實例化命令行app := cli.NewApp()// 服務的名稱app.Name = "WebService"// 服務的描述app.Description = "Web服務相關描述"// 服務的用途描述app.Usage = "webservice api --port=8080 --config=path --log_file=/usr/local/webservice/log/go_cli.log"// 服務的版本號信息app.Version = "1.0.0"// 初始化多個命令app.Commands = []cli.Command{// api命令api.Command,// service命令service.Command,}app.Before = func(context *cli.Context) error {// 實現一些邏輯return nil}app.After = func(context *cli.Context) error {// 實現一些邏輯return nil}var err = app.Run(os.Args)if err != nil {fmt.Println("app run fatal! err : ", err)} }運行結果:
1、編譯運行Api示例:
#go build -o webservice/bin/webservice go_cli.go #./webservice/bin/webservice api -port=8080 -config=path -log_file=/usr/local/webservice/log/go_cli.log api service port : 8080 config : path logfile : /usr/local/webservice/log/go_cli.log2、編譯運行Service示例:
#go build -o webservice/bin/webservice go_cli.go #./webservice/bin/webservice service -config=path -log_file=/usr/local/webservice/log/go_cli.log service config : path logfile : /usr/local/webservice/log/go_cli.log3、不傳遞任何參數的時候,會提示命令會出現HELP信息,運行如下。
#go build -o webservice/bin/webservice go_cli.go #./webservice/bin/webservice NAME:WebService - webservice api --port=8080 --config=path --log_file=/usr/local/webservice/log/go_cli.logUSAGE:go_cli.exe [global options] command [command options] [arguments...]VERSION:1.0.0DESCRIPTION:Web服務相關描述COMMANDS:apiservicehelp, h Shows a list of commands or help for one commandGLOBAL OPTIONS:--help, -h show help--version, -v print the version總結:
命令行解析上支持的比較友好,支持的內容比較全面
使用上方便,快速
總結
以上是生活随笔為你收集整理的Go语言 命令行解析(二)的全部內容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: Go语言 命令行解析(一)
- 下一篇: Go语言讲解深拷贝与浅拷贝