golang实现Cobra命令闭环应用与oh-my-posh提示增强插件库console的使用

Golang实现Cobra命令闭环应用与oh-my-posh提示增强插件库console的使用

Console是一个基于Cobra命令和readline shell构建的全功能控制台应用库,它提供了现代化的交互界面,同时允许开发者专注于核心命令的开发。

主要特性

菜单与命令

  • 绑定Cobra命令提供核心功能
  • 支持多个菜单,每个菜单有自己的命令树、提示引擎和特殊处理器
  • 可以自由修改和使用所有Cobra设置
  • 为每个菜单绑定特殊中断错误(如CtrlC/CtrlD)的处理器

Shell接口

  • 由readline实例提供支持,支持完整的inputrc功能和扩展功能
  • 可配置的键绑定、命令和选项,合理的默认值和应用特定配置
  • 开箱即用的高级命令、标志、位置参数和标志参数补全
  • 命令语法高亮

其他功能

  • 支持任意数量的历史记录源,每个菜单独立
  • 支持oh-my-posh提示,每个菜单可使用自定义配置文件
  • 可以编写和绑定应用/菜单特定的提示段
  • 提供一组现成的命令用于readline绑定/选项操作

示例代码

下面是一个完整的示例,展示如何使用console库创建一个简单的交互式应用:

package main

import (
	"fmt"

	"github.com/reeflective/console"
	"github.com/reeflective/console/example/commands"
	"github.com/spf13/cobra"
)

func main() {
	// 创建一个新的控制台实例
	con := console.New("example")

	// 设置根命令
	rootCmd := &cobra.Command{
		Use:   "example",
		Short: "An example console application",
		RunE: func(cmd *cobra.Command, args []string) error {
			return con.Start()
		},
	}

	// 添加一些示例命令
	rootCmd.AddCommand(commands.NewVersionCmd())
	rootCmd.AddCommand(commands.NewExitCmd(con))

	// 将根命令绑定到控制台
	con.SetRootCommand(rootCmd)

	// 添加一个主菜单
	mainMenu := con.AddMenu("main", "Main menu")
	mainMenu.SetCommands(rootCmd)

	// 配置oh-my-posh提示
	mainMenu.SetPrompt(
		console.Prompt{
			Primary:   "example > ",
			Secondary: "> ",
			Transient: "> ",
		},
	)

	// 添加CtrlC中断处理器
	mainMenu.InterruptHandlers(console.InterruptHandler{
		Interrupt: console.InterruptCtrlC,
		Handler: func(con *console.Console) {
			fmt.Println("\nCtrl+C pressed - use 'exit' to quit")
		},
	})

	// 启动应用
	if err := rootCmd.Execute(); err != nil {
		fmt.Println(err)
	}
}

oh-my-posh集成示例

要集成oh-my-posh提示,可以使用以下代码:

package main

import (
	"github.com/reeflective/console"
	"github.com/reeflective/console/prompt/omp"
)

func setupOMPPrompt(con *console.Console) {
	// 创建一个oh-my-posh提示引擎
	prompt := omp.NewPrompt()

	// 加载自定义主题文件
	prompt.SetConfigFile("path/to/your/theme.json")

	// 添加自定义段
	prompt.AddSegment("mysegment", func() string {
		return " [CUSTOM] "
	})

	// 将提示绑定到主菜单
	mainMenu := con.Menu("main")
	mainMenu.SetPromptEngine(prompt)
}

状态说明

该库目前处于预发布候选状态:

  • 虽然简单小巧,但尚未经过大量测试
  • 可能还有一些功能需要改进
  • API相当稳定,未来版本不太可能有大的变化

欢迎提交PR或issue来提出改进建议,也欢迎其他贡献、错误修复和代码审查。


更多关于golang实现Cobra命令闭环应用与oh-my-posh提示增强插件库console的使用的实战教程也可以访问 https://www.itying.com/category-94-b0.html

1 回复

更多关于golang实现Cobra命令闭环应用与oh-my-posh提示增强插件库console的使用的实战系列教程也可以访问 https://www.itying.com/category-94-b0.html


Golang实现Cobra命令闭环应用与oh-my-posh提示增强

1. Cobra命令闭环应用实现

Cobra是一个强大的Go命令行库,广泛用于创建CLI应用程序。下面是一个完整的Cobra命令闭环应用示例:

package main

import (
	"fmt"
	"os"

	"github.com/spf13/cobra"
)

var rootCmd = &cobra.Command{
	Use:   "myapp",
	Short: "MyApp is a sample CLI application",
	Long:  `A longer description of my application with examples and usage`,
	Run: func(cmd *cobra.Command, args []string) {
		fmt.Println("Welcome to MyApp! Use --help to see available commands.")
	},
}

var versionCmd = &cobra.Command{
	Use:   "version",
	Short: "Print the version number of MyApp",
	Run: func(cmd *cobra.Command, args []string) {
		fmt.Println("MyApp v1.0.0")
	},
}

var greetCmd = &cobra.Command{
	Use:   "greet [name]",
	Short: "Greet someone",
	Args:  cobra.MinimumNArgs(1),
	Run: func(cmd *cobra.Command, args []string) {
		fmt.Printf("Hello, %s!\n", args[0])
	},
}

func init() {
	// 添加子命令
	rootCmd.AddCommand(versionCmd)
	rootCmd.AddCommand(greetCmd)
	
	// 添加全局标志
	rootCmd.PersistentFlags().BoolP("verbose", "v", false, "verbose output")
}

func main() {
	if err := rootCmd.Execute(); err != nil {
		fmt.Println(err)
		os.Exit(1)
	}
}

关键点说明:

  1. 命令结构:每个命令都是一个cobra.Command实例
  2. 命令层级:通过AddCommand方法构建命令树
  3. 参数处理:使用Args字段验证参数数量
  4. 标志处理PersistentFlags可用于所有子命令
  5. 错误处理Execute()返回错误时进行适当处理

2. oh-my-posh提示增强

oh-my-posh是一个强大的终端提示定制工具,我们可以通过Go程序与其集成。

2.1 基本集成

package main

import (
	"fmt"
	"os"
	"os/exec"
	"runtime"
)

func setupOhMyPosh() error {
	// 检测oh-my-posh是否安装
	_, err := exec.LookPath("oh-my-posh")
	if err != nil {
		return fmt.Errorf("oh-my-posh not found. Please install it first")
	}

	// 根据操作系统设置不同的主题
	var theme string
	switch runtime.GOOS {
	case "windows":
		theme = "%USERPROFILE%/jandedobbeleer.omp.json"
	default:
		theme = "$HOME/.config/oh-my-posh/themes/jandedobbeleer.omp.json"
	}

	// 生成初始化脚本
	initScript := fmt.Sprintf("eval \"$(oh-my-posh init %s --config %s)\"", os.Getenv("SHELL"), theme)
	
	// 写入shell配置文件
	profileFile := getProfileFile()
	f, err := os.OpenFile(profileFile, os.O_APPEND|os.O_WRONLY|os.O_CREATE, 0644)
	if err != nil {
		return err
	}
	defer f.Close()

	_, err = f.WriteString("\n" + initScript + "\n")
	return err
}

func getProfileFile() string {
	switch runtime.GOOS {
	case "windows":
		return os.Getenv("USERPROFILE") + "\\.bashrc"
	case "darwin":
		return os.Getenv("HOME") + "/.zshrc"
	default:
		return os.Getenv("HOME") + "/.bashrc"
	}
}

func main() {
	err := setupOhMyPosh()
	if err != nil {
		fmt.Printf("Error setting up oh-my-posh: %v\n", err)
		os.Exit(1)
	}
	fmt.Println("oh-my-posh setup completed. Restart your terminal to see changes.")
}

2.2 动态提示增强

我们可以创建一个Go程序来动态更新oh-my-posh提示:

package main

import (
	"encoding/json"
	"fmt"
	"os"
	"path/filepath"
)

type PromptConfig struct {
	FinalSpace bool   `json:"final_space"`
	Blocks     []Block `json:"blocks"`
}

type Block struct {
	Type      string `json:"type"`
	Alignment string `json:"alignment"`
	Segments  []Segment `json:"segments"`
}

type Segment struct {
	Type    string `json:"type"`
	Style   string `json:"style"`
	PowerlineSymbol string `json:"powerline_symbol,omitempty"`
	Content string `json:"content,omitempty"`
}

func createCustomPrompt() error {
	config := PromptConfig{
		FinalSpace: true,
		Blocks: []Block{
			{
				Type:      "prompt",
				Alignment: "left",
				Segments: []Segment{
					{
						Type:    "path",
						Style:   "powerline",
						PowerlineSymbol: "",
					},
					{
						Type:    "git",
						Style:   "powerline",
						PowerlineSymbol: "",
					},
					{
						Type:    "time",
						Style:   "powerline",
						PowerlineSymbol: "",
						Content: "🕒 {{ .CurrentDate | date \"15:04\" }}",
					},
				},
			},
		},
	}

	configPath := filepath.Join(os.Getenv("HOME"), ".config", "oh-my-posh", "custom.omp.json")
	err := os.MkdirAll(filepath.Dir(configPath), 0755)
	if err != nil {
		return err
	}

	file, err := os.Create(configPath)
	if err != nil {
		return err
	}
	defer file.Close()

	encoder := json.NewEncoder(file)
	encoder.SetIndent("", "  ")
	return encoder.Encode(config)
}

func main() {
	err := createCustomPrompt()
	if err != nil {
		fmt.Printf("Error creating custom prompt: %v\n", err)
		os.Exit(1)
	}
	fmt.Println("Custom prompt configuration created successfully")
}

3. 结合Cobra和oh-my-posh

我们可以创建一个命令来管理oh-my-posh配置:

package main

import (
	"fmt"
	"os"

	"github.com/spf13/cobra"
)

var rootCmd = &cobra.Command{
	Use:   "poshctl",
	Short: "oh-my-posh configuration manager",
}

var initCmd = &cobra.Command{
	Use:   "init",
	Short: "Initialize oh-my-posh",
	Run: func(cmd *cobra.Command, args []string) {
		err := setupOhMyPosh()
		if err != nil {
			fmt.Printf("Error: %v\n", err)
			os.Exit(1)
		}
		fmt.Println("oh-my-posh initialized successfully")
	},
}

var themeCmd = &cobra.Command{
	Use:   "theme [name]",
	Short: "Set oh-my-posh theme",
	Args:  cobra.ExactArgs(1),
	Run: func(cmd *cobra.Command, args []string) {
		err := setTheme(args[0])
		if err != nil {
			fmt.Printf("Error: %v\n", err)
			os.Exit(1)
		}
		fmt.Printf("Theme set to %s\n", args[0])
	},
}

func init() {
	rootCmd.AddCommand(initCmd)
	rootCmd.AddCommand(themeCmd)
}

func main() {
	if err := rootCmd.Execute(); err != nil {
		fmt.Println(err)
		os.Exit(1)
	}
}

func setupOhMyPosh() error {
	// 实现同前
	return nil
}

func setTheme(name string) error {
	// 实现主题设置逻辑
	return nil
}

总结

  1. Cobra 提供了强大的CLI构建能力,适合创建复杂的命令行应用
  2. oh-my-posh 可以显著增强终端体验,通过Go程序可以动态管理其配置
  3. 两者结合可以创建既功能强大又美观的终端应用

实际应用中,你可以根据需求扩展这些基础代码,添加更多命令和功能,如:

  • 动态主题切换
  • 提示信息实时更新
  • 与系统深度集成
  • 用户偏好配置保存等
回到顶部