diff --git a/cmd/trace-stats-ui.go b/cmd/trace-stats-ui.go index 45826b52..62089a18 100644 --- a/cmd/trace-stats-ui.go +++ b/cmd/trace-stats-ui.go @@ -28,7 +28,7 @@ import ( "github.com/charmbracelet/bubbles/spinner" tea "github.com/charmbracelet/bubbletea" "github.com/charmbracelet/lipgloss" - humanize "github.com/dustin/go-humanize" + "github.com/dustin/go-humanize" "github.com/fatih/color" "github.com/minio/madmin-go/v3" "github.com/minio/pkg/v3/console" @@ -154,7 +154,7 @@ func (m *traceStatsUI) View() string { } t = append(t, console.Colorize("metrics-top-title", "Avg Size"), - console.Colorize("metrics-top-title", "Rate"), + console.Colorize("metrics-top-title", "Rate /min"), console.Colorize("metrics-top-title", "Errors"), ) @@ -193,24 +193,24 @@ func (m *traceStatsUI) View() string { sz := "-" rate := "-" if v.Size > 0 && v.Count > 0 { - sz = humanize.IBytes(uint64(v.Size) / uint64(v.Count)) - rate = fmt.Sprintf("%s/m", humanize.IBytes(uint64(float64(v.Size)/dur.Minutes()))) + sz = ibytesShort(uint64(v.Size) / uint64(v.Count)) + rate = ibytesShort(uint64(float64(v.Size) / dur.Minutes())) } if v.CallStatsCount > 0 { var s, r []string if v.CallStats.Rx > 0 { - s = append(s, fmt.Sprintf("↑ %s", humanize.IBytes(uint64(v.CallStats.Rx/v.CallStatsCount)))) - r = append(r, fmt.Sprintf("↑ %s", humanize.IBytes(uint64(float64(v.CallStats.Rx)/dur.Minutes())))) + s = append(s, fmt.Sprintf("↑%s", ibytesShort(uint64(v.CallStats.Rx/v.CallStatsCount)))) + r = append(r, fmt.Sprintf("↑%s", ibytesShort(uint64(float64(v.CallStats.Rx)/dur.Minutes())))) } if v.CallStats.Tx > 0 { - s = append(s, fmt.Sprintf("↓ %s", humanize.IBytes(uint64(v.CallStats.Tx/v.CallStatsCount)))) - r = append(r, fmt.Sprintf("↓ %s", humanize.IBytes(uint64(float64(v.CallStats.Tx)/dur.Minutes())))) + s = append(s, fmt.Sprintf("↓%s", ibytesShort(uint64(v.CallStats.Tx/v.CallStatsCount)))) + r = append(r, fmt.Sprintf("↓%s", ibytesShort(uint64(float64(v.CallStats.Tx)/dur.Minutes())))) } - if len(s) > 0 { + if len(s)+len(r) > 0 { sz = strings.Join(s, " ") } if len(r) > 0 { - rate = strings.Join(r, " ") + "/m" + rate = strings.Join(r, " ") } } if sz != "-" { @@ -223,14 +223,18 @@ func (m *traceStatsUI) View() string { console.Colorize("metrics-number", fmt.Sprintf("%d ", v.Count)) + console.Colorize("metrics-number-secondary", fmt.Sprintf("(%0.1f%%)", float64(v.Count)/float64(totalCnt)*100)), console.Colorize("metrics-number", fmt.Sprintf("%0.1f", float64(v.Count)/dur.Minutes())), - console.Colorize(avgColor, fmt.Sprintf("%v", avg.Round(time.Microsecond))), - console.Colorize(minColor, v.MinDur), - console.Colorize(maxColor, v.MaxDur), + console.Colorize(avgColor, fmt.Sprintf("%v", roundDur(avg))), + console.Colorize(minColor, roundDur(v.MinDur)), + console.Colorize(maxColor, roundDur(v.MaxDur)), } if hasTTFB { - t = append(t, - console.Colorize(avgColor, fmt.Sprintf("%v", avgTTFB.Round(time.Microsecond))), - console.Colorize(maxColor, v.MaxTTFB)) + if v.TTFB > 0 { + t = append(t, + console.Colorize(avgColor, fmt.Sprintf("%v", roundDur(avgTTFB))), + console.Colorize(maxColor, roundDur(v.MaxTTFB))) + } else { + t = append(t, "-", "-") + } } t = append(t, sz, rate, errs) table.Append(t) @@ -250,10 +254,31 @@ func (m *traceStatsUI) View() string { return strings.Join(split, "\n") } +// ibytesShort returns a short un-padded version of the value from humanize.IBytes. +func ibytesShort(v uint64) string { + return strings.ReplaceAll(strings.TrimSuffix(humanize.IBytes(v), "iB"), " ", "") +} + +// roundDur will round the duration to a nice, printable number, with "reasonable" precision. +func roundDur(d time.Duration) time.Duration { + if d > time.Minute { + return d.Round(time.Second) + } + if d > time.Second { + return d.Round(time.Millisecond) + } + if d > time.Millisecond { + return d.Round(time.Millisecond / 10) + } + return d.Round(time.Microsecond) +} + func initTraceStatsUI(maxEntries int, traces <-chan madmin.ServiceTraceInfo) *traceStatsUI { meter := spinner.New() meter.Spinner = spinner.Meter meter.Style = lipgloss.NewStyle().Foreground(lipgloss.Color("205")) + // Use half the default fps to reduce flickering + meter.Spinner.FPS = time.Second / 3 console.SetColor("metrics-duration", color.New(color.FgWhite)) console.SetColor("metrics-size", color.New(color.FgGreen)) console.SetColor("metrics-dur", color.New(color.FgGreen))