Go 每日一库之 cobra

2023-11-12

简介

cobra是一个命令行程序库,可以用来编写命令行程序。同时,它也提供了一个脚手架,用于生成基于 cobra 的应用程序框架。非常多知名的开源项目使用了 cobra 库构建命令行,如KubernetesHugoetcd等等等等。本文介绍 cobra 库的基本使用和一些有趣的特性。

关于作者spf13,这里多说两句。spf13 开源不少项目,而且他的开源项目质量都比较高。相信使用过 vim 的都知道spf13-vim,号称 vim 终极配置。可以一键配置,对于我这样的懒人来说绝对是福音。他的viper是一个完整的配置解决方案。完美支持 JSON/TOML/YAML/HCL/envfile/Java properties 配置文件等格式,还有一些比较实用的特性,如配置热更新、多查找目录、配置保存等。还有非常火的静态网站生成器hugo也是他的作品。

快速使用

第三方库都需要先安装,后使用。下面命令安装了cobra生成器程序和 cobra 库:

$ go get github.com/spf13/cobra/cobra

如果出现了golang.org/x/text库找不到之类的错误,需要手动从 GitHub 上下载该库,再执行上面的安装命令。我以前写过一篇博客搭建 Go 开发环境提到了这个方法。

我们实现一个简单的命令行程序 git,当然这不是真的 git,只是模拟其命令行。最终还是通过os/exec库调用外部程序执行真实的 git 命令,返回结果。所以我们的系统上要安装 git,且 git 在可执行路径中。目前我们只添加一个子命令version。目录结构如下:

▾ get-started/
    ▾ cmd/
        helper.go
        root.go
        version.go
    main.go

root.go

package cmd

import (
  "errors"

  "github.com/spf13/cobra"
)

var rootCmd = &cobra.Command {
  Use: "git",
  Short: "Git is a distributed version control system.",
  Long: `Git is a free and open source distributed version control system
designed to handle everything from small to very large projects 
with speed and efficiency.`,
  Run: func(cmd *cobra.Command, args []string) {
    Error(cmd, args, errors.New("unrecognized command"))
  },
}

func Execute() {
  rootCmd.Execute()
}

version.go

package cmd

import (
  "fmt"
  "os"

  "github.com/spf13/cobra"
)

var versionCmd = &cobra.Command {
  Use: "version",
  Short: "version subcommand show git version info.",
  
  Run: func(cmd *cobra.Command, args []string) {
    output, err := ExecuteCommand("git", "version", args...)
    if err != nil {
      Error(cmd, args, err)
    }

    fmt.Fprint(os.Stdout, output)
  },
}

func init() {
  rootCmd.AddCommand(versionCmd)
}

main.go文件中只是调用命令入口:

package main

import (
  "github.com/darjun/go-daily-lib/cobra/get-started/cmd"
)

func main() {
  cmd.Execute()
}

为了编码方便,在helpers.go中封装了调用外部程序和错误处理函数:

package cmd

import (
  "fmt"
  "os"
  "os/exec"

  "github.com/spf13/cobra"
)

func ExecuteCommand(name string, subname string, args ...string) (string, error) {
  args = append([]string{subname}, args...)

  cmd := exec.Command(name, args...)
  bytes, err := cmd.CombinedOutput()

  return string(bytes), err
}

func Error(cmd *cobra.Command, args []string, err error) {
  fmt.Fprintf(os.Stderr, "execute %s args:%v error:%v\n", cmd
本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)

Go 每日一库之 cobra 的相关文章

  • 在批处理脚本中发送 Windows 密钥

    我最近一直在使用SendKeys使用批处理脚本的函数 我已经了解如何在窗口中输入某些键 例如 Tab 键 SendKeys TAB 或者退格键 SendKeys BACKSPACE 但我一直尝试在不按Windows键的情况下输入它 不幸的是
  • formatFloat :将浮点数转换为字符串[重复]

    这个问题在这里已经有答案了 http golang org pkg strconv http golang org pkg strconv http play golang org p 4VNRgW8WoB http play golang
  • 在 Go 中使用 init() 函数真的很糟糕吗?

    几天前我开始了一个新的 go 项目 我使用 golangci lint 使我的代码具有良好的风格 我发现 gochecknoinits 是 golangci lint 的 linter 之一 它告诉我不要使用 init 在我看来 为了方便起
  • 使用 cmd.exe 更改目录并在该目录中运行命令

    我想做的就是 更改到不同驱动器的特定目录 在该目录中运行命令 例如目录 我需要使用从不同驱动器开始的 cmd exe 在一行中执行此操作 我会这样做 c cd temp dir 所以到目前为止我在一份声明中 cmd c c cd temp
  • 如何使用golang中通过引用传递的索引访问切片中的元素

    我将切片的引用传递给函数 并且我正在函数内的切片中进行更改 我还尝试使用索引访问切片中的元素 它在 golang 中抛出异常 通过引用传递的索引访问切片中的元素的最佳方法是什么 您可以在此处找到示例代码 参考 http www reddit
  • Go 中数组的嵌套结构

    我已经开始使用https mholt github io json to go https mholt github io json to go 将 API JSON 转换为 go 结构 我真的很喜欢它 但是我对如何初始化如下所示的报告定义
  • 如何使用 mongo-go-driver 有效地将 bson 转换为 json?

    我想将 bson 转换为mongo go 驱动程序 https github com mongodb mongo go driver有效地转换为 json 我应该小心处理NaN 因为json Marshal失败如果NaN存在于数据中 例如
  • 在 Go 中执行字节数组

    我正在尝试在 Go 程序中执行 shellcode 类似于使用其他语言执行此操作的方式 示例 1 C 程序中的 Shellcode https stackoverflow com questions 16626857 shellcode i
  • 在没有窗口的情况下从 C# 运行命令行并获取输出[重复]

    这个问题在这里已经有答案了 我正在尝试从 C 运行命令行脚本 我希望它在没有 shell 的情况下运行并将输出放入我的字符串输出中 它不喜欢 p StartInfo 行 我究竟做错了什么 我没有运行像 p StartInfo FileNam
  • 使用 google.protobuf.Timestamp 在 Go 中解析带有时区偏移的日期时间戳

    我正在创建一个将使用 GRPC 和 protobuf 的 Go 应用程序 我的 RPC 服务应获取包含类型的消息google protobuf Timestamp 解析它并最终将其保存在数据库中或对其执行更多操作 我对什么被认为是该类型的有
  • Google Cloud Kubernetes 上任务队列的替代方案

    我发现任务队列主要用于App Engine标准环境 我正在将现有服务从 App Engine 迁移到 Kubernetes 任务队列的一个好的替代方案是什么 推送队列是当前正在使用的队列 我在线阅读文档并浏览了此链接 何时使用 PubSub
  • Python 在 anaconda 中找不到 h2o 包

    当我尝试导入 h2o 时 我被告知该包不存在 当我尝试安装它时 它告诉我它已经存在 我尝试将其从计算机中删除并重新安装 但没有成功 此时我能想到的只是一些环境变量 C Users Lanier Anaconda2 C Users Lanie
  • 如何使用 Java 原生接口从 Java 调用 Go 函数?

    可以通过以下方式调用 C 方法JNA https en wikipedia org wiki Java Native AccessJava 中的接口 如何使用 Go 实现相同的功能 package main import fmt impor
  • 在 Go 中使用互斥锁

    我想了解互斥体是如何工作的 据我目前的理解 它是为了进行原子操作并同步对某些数据的访问 我在这里构建了一个队列数据结构的示例 https github com arnauddri algorithms blob master data st
  • Golang 优雅地关闭 HTTP 服务器并进行错误处理

    我正在让我的 HTTP 服务器正常关闭 我从帖子中获取了提示here https stackoverflow com questions 39320025 how to stop http listenandserve 并且到目前为止已经像
  • Go io.Pipe 的缓冲版本

    有缓冲版本吗io Pipe https golang org pkg io Pipe 在标准库或第三方库中 在我推出自己的库之前 上下文 我正在尝试使用这个解决方案 https stackoverflow com a 36229262 15
  • 如何分析 VSCode 中函数的性能

    我用 C Golang 编写了一个程序 如何找到占用最高 CPU 周期的函数 目的是提高正在执行的程序的性能 2021 年 10 月 金香儿哈娜 https github com hyangah宣布 tweet https twitter
  • for 循环初始值设定项中的结构

    知道为什么 for 循环初始值设定项中的这个结构表达式在编译时会出现语法错误吗 在这种情况下 指向结构的指针工作正常 但 ofc 我需要如下所示的局部变量 感谢您的建议 type Request struct id int line byt
  • 如何在特定文件夹中运行 shell 命令

    我可以用这个out err exec Command git log Output 获取将在与可执行位置相同的路径中运行的命令的输出 如何指定要在哪个文件夹中运行命令 exec Command https golang org pkg os
  • 匿名结构和空结构

    http play golang org p vhaKi5uVmm http play golang org p vhaKi5uVmm package main import fmt var battle make chan string

随机推荐

  • MySql中4种批量更新的方法

    MySql中4种批量更新的方法 mysql 批量更新共有以下四种办法1 replace into 批量更新 replace into test tbl id dr values 1 2 2 3 x y 例子 replace into boo
  • 人生顿悟之宽以待人,严以律己

    台风已经过去了 天气也渐渐地晴朗了 但是不知道为什么自己的心情却越发觉得沉重起来 总觉得生活中少了点什么 是没有了以往的激情 还是多了几分压力 看了近1个月的房子 两个人的所有积蓄加上两家人的积蓄 勉强可以付得起首付 接下去就是了无止境的房
  • 开启MySQL主从半同步复制

    记录配置mysql主从半同步复制的过程 加载lib 所有主从节点都要配置 主库 install plugin rpl semi sync master soname semisync master so 从库 install plugin
  • Android Studio从一个activity到另一个activity

    Android Studio从一个activity跳转到另一个activity 简单的跳转 创建两个activity 创建跳转按钮 在第一个activity的onCreate中添加按钮监听事件 编写内部类 button setOnClick
  • [网盘工具/百度网盘]秒传链接的使用 -2022版油猴网页脚本

    注 此项技术仅针对百度网盘有效 软件要求 Chrome或Firefox等支持tampermonkey Violentmonkey的浏览器 1 什么是秒传链接 度盘秒传链接 标准提取码 由128位 32个16进制数 128位 32个16进制数
  • Neon intrinsics

    1 介绍 在上篇中 介绍了ARM的Neon 本篇主要介绍Neon intrinsics的函数用法 也就是assembly之前的用法 NEON指令是从Armv7架构开始引入的SIMD指令 其共有16个128位寄存器 发展到最新的Arm64架构
  • mysql设置wait timeout_mysql修改wait_timeout_MySQL

    bitsCN com mysql修改wait timeout mysql mysql gt show global variables like wait timeout 其默认值为8小时 mysql的一个connection空闲时间超过8
  • TypeScript中类的继承

    特点 避免重复创建类 减少代码数量 通过extends关键字继承父类 通过super继承父类的属性和方法 实例 class Person1 定义属性 name string age number gender string construc
  • transformer序列预测示例

    本文参考 python量化 将Transformer模型用于股票价格预测 蚂蚁爱Python的博客 CSDN博客 transformer 股票 一 Transformer初步架构图 二 transformer各组件信息 1 position
  • Maven执行mvn clean compile命令遇到Fatal error compiling: 无效的标记: --release错误解决办法

    Maven执行mvn clean compile命令会报如下图所示的错误 由图可知 maven compiler plugin插件编译时用到了 release选项 而我的jdk是1 8 不支持该选项 此时我的maven compiler p
  • linux学成之路(基础篇(二十三)MySQL服务(中)

    目录 MySQL服务之SQL语句 一 SQL语句类型 一 DDL语句 二 DML语句 三 DCL语句 四 DQL 语句 二 数据库操作 一 查看 二 创建 三 进入 四 删除数据库 五 更改数据库名称 六 更改字符集 三 数据表管理 一 数
  • Hadoop HDFS shell 命令行常用操作

    前言 Hadoop HDFS shell的命令和Linux的shell命令有类似的地方 基本上会使用Linux命令的话 把HDFS的理论理解一下就可以了 一 创建文件夹 hadoop fs mkdir p
  • 【915程序设计】21西交大软件专硕915程序设计真题讲解

    28 马鞍点 include
  • 【华为OD机试c++】Excel单元格数值统计【 2023 Q1

    华为OD机试 题目列表 2023Q1 点这里 2023华为OD机试 刷题指南 点这里 题目描述 Excel 工作表中对选定区域的数值进行统计的功能非常实用 仿照Excel的这个功能 请对给定表格中选中区域中的单元格进行求和统计 并输出统计结
  • Halide学习笔记---Halide语言设计的初衷

    Halide语言设计初衷 我们正处于一个数据密集的时代 4D广场相机 图形渲染 3D打印 图像传感器 高质量医学图像等 每天生产大量的图像数据 面对这样一个图像时代 急需要针对图像处理算法设计的高性能图像处理编程语言 在这样的需求下 Hal
  • 第五届蓝桥杯——java c组 1/a 的分数称为单位分数

    形如 1 a 的分数称为单位分数 可以把1分解为若干个互不相同的单位分数之和 例如 1 1 2 1 3 1 9 1 18 1 1 2 1 3 1 10 1 15 1 1 3 1 5 1 7 1 9 1 11 1 15 1 35 1 45 1
  • 一文读懂 React16.0-16.6 新特性(实践 思考)

    首先 把我知道从16 0开始到现在为止新特性全部列举出来 v16 0 render 支持返回数组和字符串 createPortal 支持自定义 DOM 属性 Error Boundary Fiber SSR优化 减少文件体积v16 1 re
  • 对区块链钱包的简单认识

    钱包是存储和使用数字货币的工具 在区块链领域有举足轻重的地位 在对钱包分类之前 需要先理解几个概念 钱包地址 它类似于银行卡号 一个人可以拥有多张银行卡 所以他也可以拥有多个钱包地址 一个钱包地址只能对应一个私钥 在一个钱包中 可以拥有多个
  • VMware导入别人的虚拟机

    根据老师发的文件 将分卷压缩文件下载到一个文件夹中 选择解压第一个文件 即可得到所有资源 可以看出得到如下文件 这里需要导入Vmware中 我查询了几种导入的方法 1 导入OVF 首先选择导入ovf文件 直接点击打开虚拟机 选择导入Ubun
  • Go 每日一库之 cobra

    简介 cobra是一个命令行程序库 可以用来编写命令行程序 同时 它也提供了一个脚手架 用于生成基于 cobra 的应用程序框架 非常多知名的开源项目使用了 cobra 库构建命令行 如Kubernetes Hugo etcd等等等等 本文