github.com/onflow/flow-go@v0.35.7-crescendo-preview.23-atree-inlining/module/metrics/chainsync.go (about)

     1  package metrics
     2  
     3  import (
     4  	"strings"
     5  	"time"
     6  
     7  	"github.com/prometheus/client_golang/prometheus"
     8  
     9  	"github.com/onflow/flow-go/model/chainsync"
    10  	"github.com/onflow/flow-go/model/flow"
    11  )
    12  
    13  type ChainSyncCollector struct {
    14  	chainID               flow.ChainID
    15  	timeToPruned          *prometheus.HistogramVec
    16  	timeToReceived        *prometheus.HistogramVec
    17  	totalPruned           *prometheus.CounterVec
    18  	storedBlocks          *prometheus.GaugeVec
    19  	totalHeightsRequested prometheus.Counter
    20  	totalIdsRequested     prometheus.Counter
    21  }
    22  
    23  func NewChainSyncCollector(chainID flow.ChainID) *ChainSyncCollector {
    24  	return &ChainSyncCollector{
    25  		chainID: chainID,
    26  		timeToPruned: prometheus.NewHistogramVec(prometheus.HistogramOpts{
    27  			Name:      "time_to_pruned_seconds",
    28  			Namespace: namespaceChainsync,
    29  			Subsystem: subsystemSyncCore,
    30  			Help:      "the time between queueing and pruning a block in seconds",
    31  			Buckets:   []float64{.1, .25, .5, 1, 2.5, 5, 7.5, 10, 20},
    32  		}, []string{"status", "requested_by"}),
    33  		timeToReceived: prometheus.NewHistogramVec(prometheus.HistogramOpts{
    34  			Name:      "time_to_received_seconds",
    35  			Namespace: namespaceChainsync,
    36  			Subsystem: subsystemSyncCore,
    37  			Help:      "the time between queueing and receiving a block in seconds",
    38  			Buckets:   []float64{.1, .25, .5, 1, 2.5, 5, 7.5, 10, 20},
    39  		}, []string{"requested_by"}),
    40  		totalPruned: prometheus.NewCounterVec(prometheus.CounterOpts{
    41  			Name:      "blocks_pruned_total",
    42  			Namespace: namespaceChainsync,
    43  			Subsystem: subsystemSyncCore,
    44  			Help:      "the total number of blocks pruned by 'id' or 'height'",
    45  		}, []string{"requested_by"}),
    46  		storedBlocks: prometheus.NewGaugeVec(prometheus.GaugeOpts{
    47  			Name:      "blocks_stored_total",
    48  			Namespace: namespaceChainsync,
    49  			Subsystem: subsystemSyncCore,
    50  			Help:      "the total number of blocks currently stored by 'id' or 'height'",
    51  		}, []string{"requested_by"}),
    52  		totalHeightsRequested: prometheus.NewCounter(prometheus.CounterOpts{
    53  			Name:      "block_heights_requested_total",
    54  			Namespace: namespaceChainsync,
    55  			Subsystem: subsystemSyncCore,
    56  			Help:      "the total number of blocks requested by height, including retried requests for the same heights. Eg: a range of 1-10 would increase the counter by 10",
    57  		}),
    58  		totalIdsRequested: prometheus.NewCounter(prometheus.CounterOpts{
    59  			Name:      "block_ids_requested_total",
    60  			Namespace: namespaceChainsync,
    61  			Subsystem: subsystemSyncCore,
    62  			Help:      "the total number of blocks requested by id",
    63  		}),
    64  	}
    65  }
    66  
    67  func (c *ChainSyncCollector) PrunedBlockById(status *chainsync.Status) {
    68  	c.prunedBlock(status, "id")
    69  }
    70  
    71  func (c *ChainSyncCollector) PrunedBlockByHeight(status *chainsync.Status) {
    72  	c.prunedBlock(status, "height")
    73  }
    74  
    75  func (c *ChainSyncCollector) prunedBlock(status *chainsync.Status, requestedBy string) {
    76  	str := strings.ToLower(status.StatusString())
    77  
    78  	// measure the time-to-pruned
    79  	pruned := float64(time.Since(status.Queued).Milliseconds())
    80  	c.timeToPruned.With(prometheus.Labels{"status": str, "requested_by": requestedBy}).Observe(pruned)
    81  
    82  	if status.WasReceived() {
    83  		// measure the time-to-received
    84  		received := float64(status.Received.Sub(status.Queued).Milliseconds())
    85  		c.timeToReceived.With(prometheus.Labels{"requested_by": requestedBy}).Observe(received)
    86  	}
    87  }
    88  
    89  func (c *ChainSyncCollector) PrunedBlocks(totalByHeight, totalById, storedByHeight, storedById int) {
    90  	// add the total number of blocks pruned
    91  	c.totalPruned.With(prometheus.Labels{"requested_by": "id"}).Add(float64(totalById))
    92  	c.totalPruned.With(prometheus.Labels{"requested_by": "height"}).Add(float64(totalByHeight))
    93  
    94  	// update gauges
    95  	c.storedBlocks.With(prometheus.Labels{"requested_by": "id"}).Set(float64(storedById))
    96  	c.storedBlocks.With(prometheus.Labels{"requested_by": "height"}).Set(float64(storedByHeight))
    97  }
    98  
    99  func (c *ChainSyncCollector) RangeRequested(ran chainsync.Range) {
   100  	c.totalHeightsRequested.Add(float64(ran.Len()))
   101  }
   102  
   103  func (c *ChainSyncCollector) BatchRequested(batch chainsync.Batch) {
   104  	c.totalIdsRequested.Add(float64(len(batch.BlockIDs)))
   105  }