CLI фреймворки для Go (Golang): полный обзор и сравнение

Онлайн-тренажер Python для начинающих

Изучайте Python легко и без перегрузки теорией. Решайте практические задачи с автоматической проверкой, получайте подсказки на русском языке и пишите код прямо в браузере — без необходимости что-либо устанавливать.

Начать курс

CLI фреймворки для Go (Golang): подробное руководство

Go (Golang) — это язык, который идеально подходит для создания инструментов командной строки (CLI). Благодаря быстрой компиляции, встроенной поддержке конкурентности и простой дистрибуции в виде одного бинарного файла, Go стал стандартом де-факто для разработки CLI-приложений. Однако для создания сложных, удобных и масштабируемых интерфейсов командной строки одной стандартной библиотеки flag часто недостаточно. На помощь приходят специализированные фреймворки. В этой статье мы подробно рассмотрим три самых популярных CLI фреймворка для Go: Cobra, urfave/cli и Kong, сравним их возможности и покажем примеры использования.

Почему стоит использовать CLI фреймворк?

Разработка CLI-приложения с нуля может быстро превратиться в хаос, особенно когда речь идет о:

  • Поддержке вложенных команд (subcommands) и флагов.
  • Автоматической генерации справки (--help).
  • Обработке ошибок и валидации аргументов.
  • Автодополнении (bash/zsh completion).

Фреймворки решают эти проблемы, предоставляя готовую архитектуру и набор инструментов.

1. Cobra — король CLI в Go

Cobra — это самый популярный фреймворк для создания CLI на Go. Он используется в таких гигантах, как Kubernetes, Hugo, Docker и GitHub CLI. Cobra построен на концепции команд, аргументов и флагов.

Основные возможности Cobra:

  • Команды и подкоманды: Любое действие — это команда (app serve, app init).
  • Флаги: Глобальные (--verbose) и локальные для команды.
  • Автоматическая справка: Генерируется из описаний команд.
  • Автодополнение: Встроенная поддержка для bash, zsh, fish и PowerShell.
  • Генератор кода: Утилита cobra-cli создает скелет проекта.

Пример кода на Cobra:

package main

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

func main() {
    var rootCmd = &cobra.Command{
        Use:   "greet",
        Short: "Greet is a simple CLI tool",
        Long:  "A simple CLI tool to greet people.",
        Run: func(cmd *cobra.Command, args []string) {
            fmt.Println("Hello! Use 'greet hello --name' to greet someone.")
        },
    }

    var name string
    var helloCmd = &cobra.Command{
        Use:   "hello",
        Short: "Greet a person",
        Run: func(cmd *cobra.Command, args []string) {
            fmt.Printf("Hello, %s!\n", name)
        },
    }

    helloCmd.Flags().StringVarP(&name, "name", "n", "World", "Name to greet")
    rootCmd.AddCommand(helloCmd)
    rootCmd.Execute()
}

Запуск: go run main.go hello --name=PythonLib выведет Hello, PythonLib!.

2. urfave/cli — простота и минимализм

Ранее известный как codegangsta/cli, этот фреймворк славится своей простотой и элегантным API. Он отлично подходит для небольших и средних проектов, где не нужна вся мощь Cobra.

Ключевые особенности urfave/cli:

  • Декларативный стиль: Приложение описывается как структура данных.
  • Автоматическая генерация справки: Красивая и читаемая.
  • Поддержка действий: Каждая команда имеет свою функцию-обработчик.
  • Встроенные типы флагов: Строки, числа, булевы значения, длительность и даже файлы.

Пример кода на urfave/cli:

package main

import (
    "fmt"
    "log"
    "os"

    "github.com/urfave/cli/v2"
)

func main() {
    app := &cli.App{
        Name:  "calc",
        Usage: "A simple calculator",
        Commands: []*cli.Command{
            {
                Name:    "add",
                Aliases: []string{"a"},
                Usage:   "Add two numbers",
                Action: func(cCtx *cli.Context) error {
                    if cCtx.NArg() != 2 {
                        return fmt.Errorf("need exactly 2 arguments")
                    }
                    x := cCtx.Args().Get(0)
                    y := cCtx.Args().Get(1)
                    fmt.Printf("Result: %s + %s = ?\n", x, y)
                    return nil
                },
            },                    

Рекомендаций