diff --git a/Taskfile.yml b/Taskfile.yml index 47ccef9..e1e9ec8 100644 --- a/Taskfile.yml +++ b/Taskfile.yml @@ -18,7 +18,7 @@ tasks: sources: - cmd/convids/**/*.go - convids/**/*.go - - internal/cli/*.go + - cli/err/*go generates: - build/convids cmds: diff --git a/internal/cli/cli.go b/cli/err/err.go similarity index 90% rename from internal/cli/cli.go rename to cli/err/err.go index f0517dd..dcab16e 100644 --- a/internal/cli/cli.go +++ b/cli/err/err.go @@ -1,4 +1,4 @@ -package cli +package err import ( "fmt" diff --git a/cli/spin/spin.go b/cli/spin/spin.go new file mode 100644 index 0000000..dd584d8 --- /dev/null +++ b/cli/spin/spin.go @@ -0,0 +1,85 @@ +package spin + +import ( + "context" + "errors" + "fmt" + + "github.com/charmbracelet/bubbles/spinner" + tea "github.com/charmbracelet/bubbletea" +) + +type model struct { + spinner spinner.Model + text string + quitting bool + err error +} + +type errMsg error + +type textMessage string + +func newModel(text string) model { + s := spinner.New() + s.Spinner = spinner.Dot + return model{spinner: s, text: text} +} + +func (m model) Init() tea.Cmd { + return m.spinner.Tick +} + +func (m model) Update(msg tea.Msg) (tea.Model, tea.Cmd) { + switch msg := msg.(type) { + case errMsg: + m.err = msg + return m, nil + + case textMessage: + m.text = string(msg) + return m, nil + + default: + var cmd tea.Cmd + m.spinner, cmd = m.spinner.Update(msg) + return m, cmd + } +} + +func (m model) View() string { + if m.err != nil { + return m.err.Error() + } + str := fmt.Sprintf("%s %s\n", m.spinner.View(), m.text) + if m.quitting { + return str + "\n" + } + return str +} + +func Spin(ctx context.Context, message string) (chan string, chan error) { + p := tea.NewProgram(newModel(message), tea.WithContext(ctx)) + + msgChan := make(chan string, 10) + errChan := make(chan error) + + go func() { + for { + m := <-msgChan + p.Send(textMessage(m)) + } + }() + go func() { + _, err := p.Run() + if errors.Is(err, context.Canceled) { + err = nil + } else if errors.Is(err, context.DeadlineExceeded) { + err = nil + } else if errors.Is(err, tea.ErrProgramKilled) { + err = nil + } + errChan <- err + }() + return msgChan, errChan +} diff --git a/cmd/convids/main.go b/cmd/convids/main.go index f07e8db..08479a0 100644 --- a/cmd/convids/main.go +++ b/cmd/convids/main.go @@ -4,8 +4,8 @@ import ( "fmt" "os" + e "codeberg.org/danjones000/utils/cli/err" "codeberg.org/danjones000/utils/convids" - "codeberg.org/danjones000/utils/internal/cli" "github.com/spf13/pflag" ) @@ -26,11 +26,11 @@ func main() { } data, err := convids.NewData(dataPath) - cli.HandleErr(err) + e.HandleErr(err) convids.WalkFiles(data, false, false, func(s *convids.Show, path string) error { fmt.Printf("%s for %+v\n", path, s) return nil }) - fmt.Println("\nDone!") + fmt.Println("Done!") } diff --git a/convids/logic.go b/convids/logic.go index 35b1497..0962ab3 100644 --- a/convids/logic.go +++ b/convids/logic.go @@ -56,6 +56,7 @@ func WalkFiles(d *Data, stopOnError, silent bool, cb func(s *Show, path string) if err != nil && stopOnError { return } + break } } } diff --git a/convids/methods.go b/convids/methods.go index c79c873..69ce198 100644 --- a/convids/methods.go +++ b/convids/methods.go @@ -71,7 +71,7 @@ func (d *Data) AllShows(silent bool) iter.Seq[*Show] { continue } if !silent { - fmt.Println("\nChecking", show, "shows\n") + fmt.Println("Checking", show, "shows\n") } for s := range sh.All() { if s == nil { diff --git a/go.mod b/go.mod index cb0d6e9..83e42d4 100644 --- a/go.mod +++ b/go.mod @@ -3,6 +3,27 @@ module codeberg.org/danjones000/utils go 1.23.1 require ( + github.com/charmbracelet/bubbles v0.20.0 + github.com/charmbracelet/bubbletea v1.1.1 github.com/spf13/pflag v1.0.5 gopkg.in/yaml.v3 v3.0.1 ) + +require ( + github.com/aymanbagabas/go-osc52/v2 v2.0.1 // indirect + github.com/charmbracelet/lipgloss v0.13.0 // indirect + github.com/charmbracelet/x/ansi v0.2.3 // indirect + github.com/charmbracelet/x/term v0.2.0 // indirect + github.com/erikgeiser/coninput v0.0.0-20211004153227-1c3628e74d0f // indirect + github.com/lucasb-eyer/go-colorful v1.2.0 // indirect + github.com/mattn/go-isatty v0.0.20 // indirect + github.com/mattn/go-localereader v0.0.1 // indirect + github.com/mattn/go-runewidth v0.0.16 // indirect + github.com/muesli/ansi v0.0.0-20230316100256-276c6243b2f6 // indirect + github.com/muesli/cancelreader v0.2.2 // indirect + github.com/muesli/termenv v0.15.2 // indirect + github.com/rivo/uniseg v0.4.7 // indirect + golang.org/x/sync v0.8.0 // indirect + golang.org/x/sys v0.24.0 // indirect + golang.org/x/text v0.3.8 // indirect +) diff --git a/go.sum b/go.sum index dc35735..c826619 100644 --- a/go.sum +++ b/go.sum @@ -1,5 +1,44 @@ +github.com/aymanbagabas/go-osc52/v2 v2.0.1 h1:HwpRHbFMcZLEVr42D4p7XBqjyuxQH5SMiErDT4WkJ2k= +github.com/aymanbagabas/go-osc52/v2 v2.0.1/go.mod h1:uYgXzlJ7ZpABp8OJ+exZzJJhRNQ2ASbcXHWsFqH8hp8= +github.com/charmbracelet/bubbles v0.20.0 h1:jSZu6qD8cRQ6k9OMfR1WlM+ruM8fkPWkHvQWD9LIutE= +github.com/charmbracelet/bubbles v0.20.0/go.mod h1:39slydyswPy+uVOHZ5x/GjwVAFkCsV8IIVy+4MhzwwU= +github.com/charmbracelet/bubbletea v1.1.1 h1:KJ2/DnmpfqFtDNVTvYZ6zpPFL9iRCRr0qqKOCvppbPY= +github.com/charmbracelet/bubbletea v1.1.1/go.mod h1:9Ogk0HrdbHolIKHdjfFpyXJmiCzGwy+FesYkZr7hYU4= +github.com/charmbracelet/lipgloss v0.13.0 h1:4X3PPeoWEDCMvzDvGmTajSyYPcZM4+y8sCA/SsA3cjw= +github.com/charmbracelet/lipgloss v0.13.0/go.mod h1:nw4zy0SBX/F/eAO1cWdcvy6qnkDUxr8Lw7dvFrAIbbY= +github.com/charmbracelet/x/ansi v0.2.3 h1:VfFN0NUpcjBRd4DnKfRaIRo53KRgey/nhOoEqosGDEY= +github.com/charmbracelet/x/ansi v0.2.3/go.mod h1:dk73KoMTT5AX5BsX0KrqhsTqAnhZZoCBjs7dGWp4Ktw= +github.com/charmbracelet/x/term v0.2.0 h1:cNB9Ot9q8I711MyZ7myUR5HFWL/lc3OpU8jZ4hwm0x0= +github.com/charmbracelet/x/term v0.2.0/go.mod h1:GVxgxAbjUrmpvIINHIQnJJKpMlHiZ4cktEQCN6GWyF0= +github.com/erikgeiser/coninput v0.0.0-20211004153227-1c3628e74d0f h1:Y/CXytFA4m6baUTXGLOoWe4PQhGxaX0KpnayAqC48p4= +github.com/erikgeiser/coninput v0.0.0-20211004153227-1c3628e74d0f/go.mod h1:vw97MGsxSvLiUE2X8qFplwetxpGLQrlU1Q9AUEIzCaM= +github.com/lucasb-eyer/go-colorful v1.2.0 h1:1nnpGOrhyZZuNyfu1QjKiUICQ74+3FNCN69Aj6K7nkY= +github.com/lucasb-eyer/go-colorful v1.2.0/go.mod h1:R4dSotOR9KMtayYi1e77YzuveK+i7ruzyGqttikkLy0= +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/mattn/go-localereader v0.0.1 h1:ygSAOl7ZXTx4RdPYinUpg6W99U8jWvWi9Ye2JC/oIi4= +github.com/mattn/go-localereader v0.0.1/go.mod h1:8fBrzywKY7BI3czFoHkuzRoWE9C+EiG4R1k4Cjx5p88= +github.com/mattn/go-runewidth v0.0.16 h1:E5ScNMtiwvlvB5paMFdw9p4kSQzbXFikJ5SQO6TULQc= +github.com/mattn/go-runewidth v0.0.16/go.mod h1:Jdepj2loyihRzMpdS35Xk/zdY8IAYHsh153qUoGf23w= +github.com/muesli/ansi v0.0.0-20230316100256-276c6243b2f6 h1:ZK8zHtRHOkbHy6Mmr5D264iyp3TiX5OmNcI5cIARiQI= +github.com/muesli/ansi v0.0.0-20230316100256-276c6243b2f6/go.mod h1:CJlz5H+gyd6CUWT45Oy4q24RdLyn7Md9Vj2/ldJBSIo= +github.com/muesli/cancelreader v0.2.2 h1:3I4Kt4BQjOR54NavqnDogx/MIoWBFa0StPA8ELUXHmA= +github.com/muesli/cancelreader v0.2.2/go.mod h1:3XuTXfFS2VjM+HTLZY9Ak0l6eUKfijIfMUZ4EgX0QYo= +github.com/muesli/termenv v0.15.2 h1:GohcuySI0QmI3wN8Ok9PtKGkgkFIk7y6Vpb5PvrY+Wo= +github.com/muesli/termenv v0.15.2/go.mod h1:Epx+iuz8sNs7mNKhxzH4fWXGNpZwUaJKRS1noLXviQ8= +github.com/rivo/uniseg v0.2.0/go.mod h1:J6wj4VEh+S6ZtnVlnTBMWIodfgj8LQOQFoIToxlJtxc= +github.com/rivo/uniseg v0.4.7 h1:WUdvkW8uEhrYfLC4ZzdpI2ztxP1I582+49Oc5Mq64VQ= +github.com/rivo/uniseg v0.4.7/go.mod h1:FN3SvrM+Zdj16jyLfmOkMNblXMcoc8DfTHruCPUcx88= github.com/spf13/pflag v1.0.5 h1:iy+VFUOCP1a+8yFto/drg2CJ5u0yRoB7fZw3DKv/JXA= github.com/spf13/pflag v1.0.5/go.mod h1:McXfInJRrz4CZXVZOBLb0bTZqETkiAhM9Iw0y3An2Bg= +golang.org/x/sync v0.8.0 h1:3NFvSEYkUoMifnESzZl15y791HH1qU2xm6eCJU5ZPXQ= +golang.org/x/sync v0.8.0/go.mod h1:Czt+wKu1gCyEFDUtn0jG5QVvpJ6rzVqr5aXyt9drQfk= +golang.org/x/sys v0.0.0-20210809222454-d867a43fc93e/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= +golang.org/x/sys v0.6.0/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= +golang.org/x/sys v0.24.0 h1:Twjiwq9dn6R1fQcyiK+wQyHWfaz/BJB+YIpzU/Cv3Xg= +golang.org/x/sys v0.24.0/go.mod h1:/VUhepiaJMQUp4+oa/7Zr1D23ma6VTLIYjOOTFZPUcA= +golang.org/x/text v0.3.8 h1:nAL+RVCQ9uMn3vJZbV+MRnydTJFPf8qqY42YiA6MrqY= +golang.org/x/text v0.3.8/go.mod h1:E6s5w1FMmriuDzIBO73fBruAKo1PCIq6d2Q6DHfQ8WQ= gopkg.in/check.v1 v0.0.0-20161208181325-20d25e280405 h1:yhCVgyC4o1eVCa2tZl7eS0r+SDo693bJlVdllGtEeKM= gopkg.in/check.v1 v0.0.0-20161208181325-20d25e280405/go.mod h1:Co6ibVJAznAaIkqp8huTwlJQCZ016jof/cbN4VW5Yz0= gopkg.in/yaml.v3 v3.0.1 h1:fxVm/GzAzEWqLHuvctI91KS9hhNmmWOoWu0XTYJS7CA=