github.com/theQRL/go-zond@v0.1.1/metrics/timer.go (about) 1 package metrics 2 3 import ( 4 "sync" 5 "time" 6 ) 7 8 type TimerSnapshot interface { 9 HistogramSnapshot 10 MeterSnapshot 11 } 12 13 // Timers capture the duration and rate of events. 14 type Timer interface { 15 Snapshot() TimerSnapshot 16 Stop() 17 Time(func()) 18 UpdateSince(time.Time) 19 Update(time.Duration) 20 } 21 22 // GetOrRegisterTimer returns an existing Timer or constructs and registers a 23 // new StandardTimer. 24 // Be sure to unregister the meter from the registry once it is of no use to 25 // allow for garbage collection. 26 func GetOrRegisterTimer(name string, r Registry) Timer { 27 if nil == r { 28 r = DefaultRegistry 29 } 30 return r.GetOrRegister(name, NewTimer).(Timer) 31 } 32 33 // NewCustomTimer constructs a new StandardTimer from a Histogram and a Meter. 34 // Be sure to call Stop() once the timer is of no use to allow for garbage collection. 35 func NewCustomTimer(h Histogram, m Meter) Timer { 36 if !Enabled { 37 return NilTimer{} 38 } 39 return &StandardTimer{ 40 histogram: h, 41 meter: m, 42 } 43 } 44 45 // NewRegisteredTimer constructs and registers a new StandardTimer. 46 // Be sure to unregister the meter from the registry once it is of no use to 47 // allow for garbage collection. 48 func NewRegisteredTimer(name string, r Registry) Timer { 49 c := NewTimer() 50 if nil == r { 51 r = DefaultRegistry 52 } 53 r.Register(name, c) 54 return c 55 } 56 57 // NewTimer constructs a new StandardTimer using an exponentially-decaying 58 // sample with the same reservoir size and alpha as UNIX load averages. 59 // Be sure to call Stop() once the timer is of no use to allow for garbage collection. 60 func NewTimer() Timer { 61 if !Enabled { 62 return NilTimer{} 63 } 64 return &StandardTimer{ 65 histogram: NewHistogram(NewExpDecaySample(1028, 0.015)), 66 meter: NewMeter(), 67 } 68 } 69 70 // NilTimer is a no-op Timer. 71 type NilTimer struct{} 72 73 func (NilTimer) Snapshot() TimerSnapshot { return (*emptySnapshot)(nil) } 74 func (NilTimer) Stop() {} 75 func (NilTimer) Time(f func()) { f() } 76 func (NilTimer) Update(time.Duration) {} 77 func (NilTimer) UpdateSince(time.Time) {} 78 79 // StandardTimer is the standard implementation of a Timer and uses a Histogram 80 // and Meter. 81 type StandardTimer struct { 82 histogram Histogram 83 meter Meter 84 mutex sync.Mutex 85 } 86 87 // Snapshot returns a read-only copy of the timer. 88 func (t *StandardTimer) Snapshot() TimerSnapshot { 89 t.mutex.Lock() 90 defer t.mutex.Unlock() 91 return &timerSnapshot{ 92 histogram: t.histogram.Snapshot(), 93 meter: t.meter.Snapshot(), 94 } 95 } 96 97 // Stop stops the meter. 98 func (t *StandardTimer) Stop() { 99 t.meter.Stop() 100 } 101 102 // Record the duration of the execution of the given function. 103 func (t *StandardTimer) Time(f func()) { 104 ts := time.Now() 105 f() 106 t.Update(time.Since(ts)) 107 } 108 109 // Record the duration of an event. 110 func (t *StandardTimer) Update(d time.Duration) { 111 t.mutex.Lock() 112 defer t.mutex.Unlock() 113 t.histogram.Update(int64(d)) 114 t.meter.Mark(1) 115 } 116 117 // Record the duration of an event that started at a time and ends now. 118 func (t *StandardTimer) UpdateSince(ts time.Time) { 119 t.mutex.Lock() 120 defer t.mutex.Unlock() 121 t.histogram.Update(int64(time.Since(ts))) 122 t.meter.Mark(1) 123 } 124 125 // timerSnapshot is a read-only copy of another Timer. 126 type timerSnapshot struct { 127 histogram HistogramSnapshot 128 meter MeterSnapshot 129 } 130 131 // Count returns the number of events recorded at the time the snapshot was 132 // taken. 133 func (t *timerSnapshot) Count() int64 { return t.histogram.Count() } 134 135 // Max returns the maximum value at the time the snapshot was taken. 136 func (t *timerSnapshot) Max() int64 { return t.histogram.Max() } 137 138 // Size returns the size of the sample at the time the snapshot was taken. 139 func (t *timerSnapshot) Size() int { return t.histogram.Size() } 140 141 // Mean returns the mean value at the time the snapshot was taken. 142 func (t *timerSnapshot) Mean() float64 { return t.histogram.Mean() } 143 144 // Min returns the minimum value at the time the snapshot was taken. 145 func (t *timerSnapshot) Min() int64 { return t.histogram.Min() } 146 147 // Percentile returns an arbitrary percentile of sampled values at the time the 148 // snapshot was taken. 149 func (t *timerSnapshot) Percentile(p float64) float64 { 150 return t.histogram.Percentile(p) 151 } 152 153 // Percentiles returns a slice of arbitrary percentiles of sampled values at 154 // the time the snapshot was taken. 155 func (t *timerSnapshot) Percentiles(ps []float64) []float64 { 156 return t.histogram.Percentiles(ps) 157 } 158 159 // Rate1 returns the one-minute moving average rate of events per second at the 160 // time the snapshot was taken. 161 func (t *timerSnapshot) Rate1() float64 { return t.meter.Rate1() } 162 163 // Rate5 returns the five-minute moving average rate of events per second at 164 // the time the snapshot was taken. 165 func (t *timerSnapshot) Rate5() float64 { return t.meter.Rate5() } 166 167 // Rate15 returns the fifteen-minute moving average rate of events per second 168 // at the time the snapshot was taken. 169 func (t *timerSnapshot) Rate15() float64 { return t.meter.Rate15() } 170 171 // RateMean returns the meter's mean rate of events per second at the time the 172 // snapshot was taken. 173 func (t *timerSnapshot) RateMean() float64 { return t.meter.RateMean() } 174 175 // StdDev returns the standard deviation of the values at the time the snapshot 176 // was taken. 177 func (t *timerSnapshot) StdDev() float64 { return t.histogram.StdDev() } 178 179 // Sum returns the sum at the time the snapshot was taken. 180 func (t *timerSnapshot) Sum() int64 { return t.histogram.Sum() } 181 182 // Variance returns the variance of the values at the time the snapshot was 183 // taken. 184 func (t *timerSnapshot) Variance() float64 { return t.histogram.Variance() }