zrepl status: hide progress bar once all filesystems reach terminal state (#674)

* Added `IsTerminal` method
* Made rendering of progress bar conditional based on IsTerminal
This commit is contained in:
Tercio Filho 2023-05-02 14:28:56 -03:00 committed by GitHub
parent 2b3df7e342
commit 2b3daaf9f1
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
3 changed files with 40 additions and 15 deletions

View File

@ -374,13 +374,15 @@ func renderReplicationReport(t *stringbuilder.B, rep *report.Report, history *by
eta = time.Duration((float64(expected)-float64(replicated))/float64(rate)) * time.Second eta = time.Duration((float64(expected)-float64(replicated))/float64(rate)) * time.Second
} }
t.Write("Progress: ") if !latest.State.IsTerminal() {
t.DrawBar(50, replicated, expected, changeCount) t.Write("Progress: ")
t.Write(fmt.Sprintf(" %s / %s @ %s/s", ByteCountBinaryUint(replicated), ByteCountBinaryUint(expected), ByteCountBinary(rate))) t.DrawBar(50, replicated, expected, changeCount)
if eta != 0 { t.Write(fmt.Sprintf(" %s / %s @ %s/s", ByteCountBinaryUint(replicated), ByteCountBinaryUint(expected), ByteCountBinary(rate)))
t.Write(fmt.Sprintf(" (%s remaining)", humanizeDuration(eta))) if eta != 0 {
t.Write(fmt.Sprintf(" (%s remaining)", humanizeDuration(eta)))
}
t.Newline()
} }
t.Newline()
if containsInvalidSizeEstimates { if containsInvalidSizeEstimates {
t.Write("NOTE: not all steps could be size-estimated, total estimate is likely imprecise!") t.Write("NOTE: not all steps could be size-estimated, total estimate is likely imprecise!")
t.Newline() t.Newline()
@ -493,15 +495,17 @@ func renderPrunerReport(t *stringbuilder.B, r *pruner.Report, fsfilter FilterFun
} }
// global progress bar // global progress bar
progress := int(math.Round(80 * float64(completedDestroyCount) / float64(totalDestroyCount))) if !state.IsTerminal() {
t.Write("Progress: ") progress := int(math.Round(80 * float64(completedDestroyCount) / float64(totalDestroyCount)))
t.Write("[") t.Write("Progress: ")
t.Write(stringbuilder.Times("=", progress)) t.Write("[")
t.Write(">") t.Write(stringbuilder.Times("=", progress))
t.Write(stringbuilder.Times("-", 80-progress)) t.Write(">")
t.Write("]") t.Write(stringbuilder.Times("-", 80-progress))
t.Printf(" %d/%d snapshots", completedDestroyCount, totalDestroyCount) t.Write("]")
t.Newline() t.Printf(" %d/%d snapshots", completedDestroyCount, totalDestroyCount)
t.Newline()
}
sort.SliceStable(all, func(i, j int) bool { sort.SliceStable(all, func(i, j int) bool {
return strings.Compare(all[i].Filesystem, all[j].Filesystem) == -1 return strings.Compare(all[i].Filesystem, all[j].Filesystem) == -1

View File

@ -199,6 +199,16 @@ const (
Done Done
) )
// Returns true in case the State is a terminal state(PlanErr, ExecErr, Done)
func (s State) IsTerminal() bool {
switch s {
case PlanErr, ExecErr, Done:
return true
default:
return false
}
}
type updater func(func(*Pruner)) type updater func(func(*Pruner))
func (p *Pruner) Prune() { func (p *Pruner) Prune() {

View File

@ -192,3 +192,14 @@ func (r *Report) GetFailedFilesystemsCountInLatestAttempt() int {
return 0 return 0
} }
} }
// Returns true in case the AttemptState is a terminal
// state(AttemptPlanningError, AttemptFanOutError, AttemptDone)
func (a AttemptState) IsTerminal() bool {
switch a {
case AttemptPlanningError, AttemptFanOutError, AttemptDone:
return true
default:
return false
}
}