[go-fan] Go Module Review: charm.land/bubbles/v2 #25594
Replies: 1 comment
-
|
💥 WHOOSH! 🦸 KAPOW! The Smoke Test Agent bursts through the wall like a comet from the outer reaches of CI space! "I have scanned your modules, analyzed your bubbly progress bars, and emerged VICTORIOUS!" — The Agent 🌟 SMOKE TEST AGENT WAS HERE — Run §24239413809 complete! All systems NOMINAL! BAM! POW! ZZZAP! 🔥
|
Beta Was this translation helpful? Give feedback.
0 replies
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Uh oh!
There was an error while loading. Please reload this page.
-
Today's module pick:
charm.land/bubbles/v2(charmbracelet/bubbles v2.1.0) — selected as the most recently updated eligible dependency (released 2026-03-26, not reviewed in the last 7 days).Module Overview
Bubbles is Charm's official component library for Bubble Tea TUI applications. It ships production-tested primitives — spinner, progress bar, textarea, textinput, viewport, table, list, file picker, paginator, help, key bindings, timer, and stopwatch — all following the Elm Architecture (
Init/Update/View).The
v2series aligns with the Bubble Tea v2 API (newtea.Viewreturn type, revised message types).Current Usage in gh-aw
Only 2 components from this 14-component library are currently used:
spinnerpkg/console/spinner.gospinner.New(),WithSpinner(MiniDot),WithStyle(),spinner.TickMsgprogresspkg/console/progress.goprogress.New(),WithColors(),WithScaled(),WithWidth(),ViewAs()Spinner pattern — uses a non-standard but correct
WithoutRenderer()approach: the spinner runs in a side-channeltea.Programon stderr while huh forms can safely take over stdin.tea.WithInput(nil)explicitly prevents the spinner from consuming keystrokes. The goroutine lifecycle is well-managed: mutex-guarded start/stop,sync.WaitGroupfor clean shutdown.Progress bar pattern — uses
ViewAs(float64)for static (non-animated) rendering, bypassing the spring animation system. Two modes are supported:ViewAs(current/total)— clean and idiomatic.pulsePercentviaupdateCount % 8to simulate a pulsing bar.Research Findings
Recent Updates — v2.1.0 (2026-03-26)
The headline feature is dynamic textarea height:
This is directly relevant if the project ever needs multi-line input outside a
huhform context.Key
progressAPIs Worth KnowingBest Practices from Maintainers
ViewAs()when calling from outside a Bubble Tea program (no commands needed).SetPercent()+Update()when inside a Bubble Tea program for smooth spring animation.WithScaled(true)(used in gh-aw) scales the gradient to match filled width — gives a more visually satisfying graduated fill at partial completion.Improvement Opportunities
🏃 Quick Wins
1. Smoother indeterminate pulsing animation
The current code in
progress.go:105-113uses 8 linear steps (updateCount % 8), which creates a stepped — not smooth — visual:Replacing with a sine wave would eliminate the stepping:
This produces a smooth 0.3→0.7→0.3 oscillation with 8 steps per cycle.
2. Terminal-width-aware progress bar
The progress bar width is hardcoded to
40(progress.WithWidth(40)). Iftty.GetTerminalWidth()is available, the bar could fill available horizontal space, looking more polished on wide terminals:3.
WithColorFuncfor contextual colorsThe current gradient (purple→cyan) is always the same.
WithColorFuncallows the color to encode semantics:✨ Feature Opportunities
Bubbles components not yet used that could benefit gh-aw:
textarea(v2.1.0)viewportfilepickertableThe
bubbles/viewportis particularly interesting: the project currently useslipgloss.JoinVerticalto compose and print sections, but has no way to make long output scrollable. A viewport in a short-lived Bubble Tea program could paginate long results.📐 Best Practice Alignment
The current usage is mostly idiomatic with a few notes:
WithoutRenderer()+ manual ANSI for spinner side-channel — correct and intentional.tea.WithInput(nil)prevents spinner from consuming form input — well thought out.ViewAs()(notView()) for static progress — correct choice.ViewAs()-based rendering but the stepping is visible.🔧 General Improvements
The project owns 14 components but uses 2. Before building custom TUI widgets, it's worth checking if bubbles already has it:
list.go:showTextList) →bubbles/listhandles this with filtering and pagination.RenderTitleBoxinconsole.go→bubbles/viewportcould manage these as scrollable sections.Recommendations
updateCount % 8linear steps withmath.Sinfor smooth indeterminate pulsingtty.GetTerminalWidth()bubbles/viewportfor long-output scrolling (verbose compile results, YAML previews)bubbles/textareaDynamicHeightis available if multi-line input is ever needed outside huh formsbubbles/filepickeris production-ready if interactive file selection is addedNext Steps
bubbles/viewportfor long compile/lint output displaymath.Sin-based) for visual polishWithoutRenderer()spinner pattern as an architectural decision commentModule summary saved to:
scratchpad/mods/bubbles.mdReferences:
Beta Was this translation helpful? Give feedback.
All reactions