diff --git a/go.mod b/go.mod index 9697dfa..e1f09c7 100644 --- a/go.mod +++ b/go.mod @@ -5,6 +5,10 @@ go 1.26.0 require github.com/spf13/cobra v1.10.2 require ( + github.com/fatih/color v1.18.0 // indirect github.com/inconshreveable/mousetrap v1.1.0 // indirect + github.com/mattn/go-colorable v0.1.13 // indirect + github.com/mattn/go-isatty v0.0.20 // indirect github.com/spf13/pflag v1.0.9 // indirect + golang.org/x/sys v0.25.0 // indirect ) diff --git a/go.sum b/go.sum index a6ee3e0..d39b047 100644 --- a/go.sum +++ b/go.sum @@ -1,10 +1,21 @@ github.com/cpuguy83/go-md2man/v2 v2.0.6/go.mod h1:oOW0eioCTA6cOiMLiUPZOpcVxMig6NIQQ7OS05n1F4g= +github.com/fatih/color v1.18.0 h1:S8gINlzdQ840/4pfAwic/ZE0djQEH3wM94VfqLTZcOM= +github.com/fatih/color v1.18.0/go.mod h1:4FelSpRwEGDpQ12mAdzqdOukCy4u8WUtOY6lkT/6HfU= github.com/inconshreveable/mousetrap v1.1.0 h1:wN+x4NVGpMsO7ErUn/mUI3vEoE6Jt13X2s0bqwp9tc8= github.com/inconshreveable/mousetrap v1.1.0/go.mod h1:vpF70FUmC8bwa3OWnCshd2FqLfsEA9PFc4w1p2J65bw= +github.com/mattn/go-colorable v0.1.13 h1:fFA4WZxdEF4tXPZVKMLwD8oUnCTTo08duU7wxecdEvA= +github.com/mattn/go-colorable v0.1.13/go.mod h1:7S9/ev0klgBDR4GtXTXX8a3vIGJpMovkB8vQcUbaXHg= +github.com/mattn/go-isatty v0.0.16/go.mod h1:kYGgaQfpe5nmfYZH+SKPsOc2e4SrIfOl2e/yFXSvRLM= +github.com/mattn/go-isatty v0.0.20 h1:xfD0iDuEKnDkl03q4limB+vH+GxLEtL/jb4xVJSWWEY= +github.com/mattn/go-isatty v0.0.20/go.mod h1:W+V8PltTTMOvKvAeJH7IuucS94S2C6jfK/D7dTCTo3Y= github.com/russross/blackfriday/v2 v2.1.0/go.mod h1:+Rmxgy9KzJVeS9/2gXHxylqXiyQDYRxCVz55jmeOWTM= github.com/spf13/cobra v1.10.2 h1:DMTTonx5m65Ic0GOoRY2c16WCbHxOOw6xxezuLaBpcU= github.com/spf13/cobra v1.10.2/go.mod h1:7C1pvHqHw5A4vrJfjNwvOdzYu0Gml16OCs2GRiTUUS4= github.com/spf13/pflag v1.0.9 h1:9exaQaMOCwffKiiiYk6/BndUBv+iRViNW+4lEMi0PvY= github.com/spf13/pflag v1.0.9/go.mod h1:McXfInJRrz4CZXVZOBLb0bTZqETkiAhM9Iw0y3An2Bg= go.yaml.in/yaml/v3 v3.0.4/go.mod h1:DhzuOOF2ATzADvBadXxruRBLzYTpT36CKvDb3+aBEFg= +golang.org/x/sys v0.0.0-20220811171246-fbc7d0a398ab/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= +golang.org/x/sys v0.6.0/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= +golang.org/x/sys v0.25.0 h1:r+8e+loiHxRqhXVl6ML1nO3l1+oFoWbnlu2Ehimmi34= +golang.org/x/sys v0.25.0/go.mod h1:/VUhepiaJMQUp4+oa/7Zr1D23ma6VTLIYjOOTFZPUcA= gopkg.in/check.v1 v0.0.0-20161208181325-20d25e280405/go.mod h1:Co6ibVJAznAaIkqp8huTwlJQCZ016jof/cbN4VW5Yz0= diff --git a/internal/reporter/reporter.go b/internal/reporter/reporter.go index 6717082..81760c8 100644 --- a/internal/reporter/reporter.go +++ b/internal/reporter/reporter.go @@ -3,22 +3,23 @@ package reporter import ( "fmt" "io" + + "github.com/space-code/linkctl/pkg/iostreams" ) func PrintBanner(w io.Writer) { fmt.Println(w, "Debugger") } -func PrintDeviceList(w io.Writer, platform string, devices []string) { +func PrintDeviceList(w io.Writer, cs *iostreams.ColorScheme, platform string, devices []string) { if len(devices) == 0 { - fmt.Fprintf(w, " No %s devices found (booted / connected)\n\n", platform) + fmt.Fprintf(w, " %s No %s devices found (booted / connected)\n\n", "⚠️", platform) return } - fmt.Fprintf(w, "%s\n", platform) - + fmt.Fprintf(w, "%s\n", cs.Bold(platform)) for _, d := range devices { - fmt.Fprintf(w, "%s %s\n", "*", d) + fmt.Fprintf(w, "%s %s\n", cs.Muted("•"), d) } fmt.Fprintln(w) } diff --git a/pkg/cmd/devices/devices.go b/pkg/cmd/devices/devices.go index 4bcbf31..6f2ac56 100644 --- a/pkg/cmd/devices/devices.go +++ b/pkg/cmd/devices/devices.go @@ -54,6 +54,7 @@ func run(f *cmdutil.Factory, opts *options) error { } w := f.IOStreams.Out - reporter.PrintDeviceList(w, "iOS", iosDevices) + cs := f.IOStreams.ColorScheme() + reporter.PrintDeviceList(w, cs, "iOS", iosDevices) return nil } diff --git a/pkg/iostreams/iostreams.go b/pkg/iostreams/iostreams.go index ad009a8..08d63cf 100644 --- a/pkg/iostreams/iostreams.go +++ b/pkg/iostreams/iostreams.go @@ -4,6 +4,8 @@ import ( "bytes" "io" "os" + + "github.com/fatih/color" ) type fileWriter interface { @@ -20,6 +22,8 @@ type IOStreams struct { In fileReader Out fileWriter ErrOut fileWriter + + colorEnabled bool } func System() *IOStreams { @@ -29,6 +33,8 @@ func System() *IOStreams { ErrOut: os.Stderr, } + ios.colorEnabled = !color.NoColor + return ios } @@ -42,13 +48,57 @@ func Test() (*IOStreams, *bytes.Buffer, *bytes.Buffer, *bytes.Buffer) { fd: 0, ReadCloser: io.NopCloser(in), }, - Out: &fdWriter{fd: 1, Writer: out}, - ErrOut: &fdWriter{fd: 2, Writer: errOut}, + Out: &fdWriter{fd: 1, Writer: out}, + ErrOut: &fdWriter{fd: 2, Writer: errOut}, + colorEnabled: false, } return io, in, out, errOut } +func (ios *IOStreams) ColorEnabled() bool { + return ios.colorEnabled +} + +type ColorScheme struct { + enabled bool +} + +func (ios *IOStreams) ColorScheme() *ColorScheme { + return &ColorScheme{enabled: ios.colorEnabled} +} + +func (cs *ColorScheme) format(c *color.Color, s string) string { + if !cs.enabled { + return s + } + return c.Sprint(s) +} + +func (cs *ColorScheme) Bold(s string) string { + return cs.format(color.New(color.Bold), s) +} + +func (cs *ColorScheme) Green(s string) string { + return cs.format(color.New(color.FgGreen), s) +} + +func (cs *ColorScheme) Cyan(s string) string { + return cs.format(color.New(color.FgCyan), s) +} + +func (cs *ColorScheme) Yellow(s string) string { + return cs.format(color.New(color.FgYellow), s) +} + +func (cs *ColorScheme) Red(s string) string { + return cs.format(color.New(color.FgRed), s) +} + +func (cs *ColorScheme) Muted(s string) string { + return cs.format(color.New(color.FgHiBlack), s) +} + type fdWriter struct { io.Writer fd uintptr