1
0
mirror of https://github.com/tw93/Mole.git synced 2026-03-22 19:40:07 +00:00

feat(status): add --json flag for programmatic access (#529)

Add --json command-line flag to mo status that outputs system metrics
in JSON format without requiring a TTY environment.

This enables:
- Integration with GUI applications (e.g., native macOS apps)
- Use in automation scripts and monitoring systems
- Piping output to tools like jq for data extraction
- Recording metrics for analysis

Implementation:
- Add JSON struct tags to all metric types
- Add --json flag using Go's flag package
- Implement runJSONMode() for one-time metric collection
- Refactor main() to support both TUI and JSON modes
- Maintain 100% backward compatibility (default TUI unchanged)

Testing:
- All 454 existing tests pass
- JSON output validated with jq and python json.tool
- Pipeline and redirection work correctly
- No breaking changes to existing functionality
This commit is contained in:
Noah Qin
2026-03-03 16:05:55 +08:00
committed by GitHub
parent 87bf90f712
commit 2a4eaf007b
2 changed files with 125 additions and 92 deletions

View File

@@ -2,6 +2,8 @@
package main
import (
"encoding/json"
"flag"
"fmt"
"os"
"path/filepath"
@@ -17,6 +19,9 @@ const refreshInterval = time.Second
var (
Version = "dev"
BuildTime = ""
// Command-line flags
jsonOutput = flag.Bool("json", false, "output metrics as JSON instead of TUI")
)
type tickMsg struct{}
@@ -204,10 +209,38 @@ func animTickWithSpeed(cpuUsage float64) tea.Cmd {
return tea.Tick(time.Duration(interval)*time.Millisecond, func(time.Time) tea.Msg { return animTickMsg{} })
}
func main() {
// runJSONMode collects metrics once and outputs as JSON.
func runJSONMode() {
collector := NewCollector()
data, err := collector.Collect()
if err != nil {
fmt.Fprintf(os.Stderr, "error collecting metrics: %v\n", err)
os.Exit(1)
}
encoder := json.NewEncoder(os.Stdout)
encoder.SetIndent("", " ")
if err := encoder.Encode(data); err != nil {
fmt.Fprintf(os.Stderr, "error encoding JSON: %v\n", err)
os.Exit(1)
}
}
// runTUIMode runs the interactive terminal UI.
func runTUIMode() {
p := tea.NewProgram(newModel(), tea.WithAltScreen())
if _, err := p.Run(); err != nil {
fmt.Fprintf(os.Stderr, "system status error: %v\n", err)
os.Exit(1)
}
}
func main() {
flag.Parse()
if *jsonOutput {
runJSONMode()
} else {
runTUIMode()
}
}