go.ligato.io/vpp-agent/v3@v3.5.0/pkg/metrics/metrics.go (about) 1 // Copyright (c) 2019 Cisco and/or its affiliates. 2 // 3 // Licensed under the Apache License, Version 2.0 (the "License"); 4 // you may not use this file except in compliance with the License. 5 // You may obtain a copy of the License at: 6 // 7 // http://www.apache.org/licenses/LICENSE-2.0 8 // 9 // Unless required by applicable law or agreed to in writing, software 10 // distributed under the License is distributed on an "AS IS" BASIS, 11 // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 12 // See the License for the specific language governing permissions and 13 // limitations under the License. 14 15 package metrics 16 17 import ( 18 "encoding/json" 19 "math" 20 "sort" 21 "time" 22 ) 23 24 // RoundDuration is the default value used for rounding durations. 25 var RoundDuration = time.Millisecond * 1 26 27 type Calls map[string]*CallStats 28 29 func (m Calls) Copy() Calls { 30 calls := make(Calls) 31 for k, s := range m { 32 copy := *s 33 calls[k] = © 34 } 35 return calls 36 } 37 38 // MarshalJSON implements json.Marshaler interface 39 func (m Calls) MarshalJSON() ([]byte, error) { 40 calls := make([]*CallStats, 0, len(m)) 41 for _, s := range m { 42 calls = append(calls, s) 43 } 44 sort.Slice(calls, func(i, j int) bool { 45 return calls[i].Count > calls[j].Count 46 }) 47 48 return json.Marshal(calls) 49 } 50 51 // CallStats represents generic stats for call metrics. 52 type CallStats struct { 53 Name string `json:"name,omitempty"` 54 Count uint64 `json:"count"` 55 Total float64 `json:"total,omitempty"` 56 Avg float64 `json:"avg,omitempty"` 57 Min float64 `json:"min,omitempty"` 58 Max float64 `json:"max,omitempty"` 59 } 60 61 // Increment increments call count and recalculates durations 62 func (m *CallStats) Increment(d time.Duration) { 63 took := d.Round(RoundDuration).Seconds() 64 m.Count++ 65 m.Total = round(m.Total + took) 66 m.Avg = round(m.Total / float64(m.Count)) 67 if took > m.Max { 68 m.Max = took 69 } 70 if m.Min == 0 || took < m.Min { 71 m.Min = took 72 } 73 } 74 75 func round(n float64) float64 { 76 return math.Round(n*1000) / 1000 77 }