github.com/cloudberrydb/gpbackup@v1.0.3-0.20240118031043-5410fd45eed6/utils/progress_bar.go (about)

     1  package utils
     2  
     3  /*
     4   * This file contains structs and functions related to logging.
     5   */
     6  
     7  import (
     8  	"time"
     9  
    10  	"github.com/cloudberrydb/gp-common-go-libs/gplog"
    11  	"gopkg.in/cheggaaa/pb.v1"
    12  )
    13  
    14  /*
    15   * Progress bar functions
    16   */
    17  
    18  /*
    19   * The following constants are used for determining when to display a progress bar
    20   *
    21   * PB_INFO only shows in info mode because some methods have a different way of
    22   * logging in verbose mode and we don't want them to conflict
    23   * PB_VERBOSE show a progress bar in INFO and VERBOSE mode
    24   *
    25   * A simple incremental progress tracker will be shown in info mode and
    26   * in verbose mode we will log progress at increments of 10%
    27   */
    28  const (
    29  	PB_NONE = iota
    30  	PB_INFO
    31  	PB_VERBOSE
    32  
    33  	//Verbose progress bar logs every 10 percent
    34  	INCR_PERCENT = 10
    35  )
    36  
    37  func NewProgressBar(count int, prefix string, showProgressBar int) ProgressBar {
    38  	progressBar := pb.New(count).Prefix(prefix)
    39  	progressBar.ShowTimeLeft = false
    40  	progressBar.SetMaxWidth(100)
    41  	progressBar.SetRefreshRate(time.Millisecond * 200)
    42  	progressBar.NotPrint = !(showProgressBar >= PB_INFO && count > 0 && gplog.GetVerbosity() == gplog.LOGINFO)
    43  	if showProgressBar == PB_VERBOSE {
    44  		verboseProgressBar := NewVerboseProgressBar(count, prefix)
    45  		verboseProgressBar.ProgressBar = progressBar
    46  		return verboseProgressBar
    47  	}
    48  	return progressBar
    49  }
    50  
    51  type ProgressBar interface {
    52  	Start() *pb.ProgressBar
    53  	Finish()
    54  	Increment() int
    55  	Add(int) int
    56  }
    57  
    58  type VerboseProgressBar struct {
    59  	current            int
    60  	total              int
    61  	prefix             string
    62  	nextPercentToPrint int
    63  	*pb.ProgressBar
    64  }
    65  
    66  func NewVerboseProgressBar(count int, prefix string) *VerboseProgressBar {
    67  	newPb := VerboseProgressBar{total: count, prefix: prefix, nextPercentToPrint: INCR_PERCENT}
    68  	return &newPb
    69  }
    70  
    71  func (vpb *VerboseProgressBar) Increment() int {
    72  	vpb.ProgressBar.Increment()
    73  	if vpb.current < vpb.total {
    74  		vpb.current++
    75  		vpb.checkPercent()
    76  	}
    77  	return vpb.current
    78  }
    79  
    80  /*
    81   * If progress bar reaches a percentage that is a multiple of 10, log a message to stdout
    82   * We increment nextPercentToPrint so the same percentage will not be printed multiple times
    83   */
    84  func (vpb *VerboseProgressBar) checkPercent() {
    85  	currPercent := int(float64(vpb.current) / float64(vpb.total) * 100)
    86  	//closestMult is the nearest percentage <= currPercent that is a multiple of 10
    87  	closestMult := currPercent / INCR_PERCENT * INCR_PERCENT
    88  	if closestMult >= vpb.nextPercentToPrint {
    89  		vpb.nextPercentToPrint = closestMult
    90  		gplog.Verbose("%s %d%% (%d/%d)", vpb.prefix, vpb.nextPercentToPrint, vpb.current, vpb.total)
    91  		vpb.nextPercentToPrint += INCR_PERCENT
    92  	}
    93  }