#Lab 02: Build a CLI Tool with Go
Create a professional CLI tool using Go and Cobra.
#šÆ Objectives
- Set up a Go project with modules
- Build a CLI with Cobra
- Implement health check commands
#š Prerequisites
- Go 1.20+ installed
- Basic Go knowledge
#š¬ Lab Steps
#Step 1: Project Setup
bash
1mkdir server-cli
2cd server-cli
3go mod init github.com/yourusername/server-cli
4go get github.com/spf13/cobra@latest#Step 2: Create Main File
Create main.go:
go
1package main
2
3import (
4 "github.com/yourusername/server-cli/cmd"
5)
6
7func main() {
8 cmd.Execute()
9}#Step 3: Create Root Command
Create cmd/root.go:
go
1package cmd
2
3import (
4 "fmt"
5 "os"
6
7 "github.com/spf13/cobra"
8)
9
10var cfgFile string
11
12var rootCmd = &cobra.Command{
13 Use: "server-cli",
14 Short: "A CLI tool for server management",
15 Long: `A DevOps CLI tool for managing and monitoring servers.`,
16}
17
18func Execute() {
19 if err := rootCmd.Execute(); err != nil {
20 fmt.Println(err)
21 os.Exit(1)
22 }
23}
24
25func init() {
26 rootCmd.PersistentFlags().StringVar(&cfgFile, "config", "",
27 "config file (default is ./config.yaml)")
28}#Step 4: Create Health Command
Create cmd/health.go:
go
1package cmd
2
3import (
4 "fmt"
5 "net"
6 "sync"
7 "time"
8
9 "github.com/spf13/cobra"
10)
11
12type Server struct {
13 Name string
14 Host string
15 Port int
16}
17
18type Result struct {
19 Server Server
20 Healthy bool
21 Latency time.Duration
22 Error string
23}
24
25var healthCmd = &cobra.Command{
26 Use: "health",
27 Short: "Check server health",
28 Run: runHealthCheck,
29}
30
31func init() {
32 rootCmd.AddCommand(healthCmd)
33}
34
35func checkHealth(server Server) Result {
36 start := time.Now()
37 address := fmt.Sprintf("%s:%d", server.Host, server.Port)
38
39 conn, err := net.DialTimeout("tcp", address, 5*time.Second)
40 if err != nil {
41 return Result{Server: server, Healthy: false, Error: err.Error()}
42 }
43 defer conn.Close()
44
45 return Result{
46 Server: server,
47 Healthy: true,
48 Latency: time.Since(start),
49 }
50}
51
52func runHealthCheck(cmd *cobra.Command, args []string) {
53 servers := []Server{
54 {Name: "Google", Host: "google.com", Port: 443},
55 {Name: "GitHub", Host: "github.com", Port: 443},
56 }
57
58 var wg sync.WaitGroup
59 results := make(chan Result, len(servers))
60
61 fmt.Println("š Checking servers...")
62
63 for _, server := range servers {
64 wg.Add(1)
65 go func(s Server) {
66 defer wg.Done()
67 results <- checkHealth(s)
68 }(server)
69 }
70
71 wg.Wait()
72 close(results)
73
74 healthyCount := 0
75 for result := range results {
76 if result.Healthy {
77 fmt.Printf("ā
%s: healthy (%v)\n", result.Server.Name, result.Latency)
78 healthyCount++
79 } else {
80 fmt.Printf("ā %s: %s\n", result.Server.Name, result.Error)
81 }
82 }
83
84 fmt.Printf("\nš %d/%d servers healthy\n", healthyCount, len(servers))
85}#Step 5: Build and Run
bash
1# Build
2go build -o server-cli .
3
4# Run
5./server-cli health#ā Success Criteria
- CLI builds successfully
- Health command works
- Parallel checks execute properly
#š What You Learned
- Go project structure
- Cobra CLI framework
- Goroutines and channels
- TCP health checks