-
Notifications
You must be signed in to change notification settings - Fork 843
/
metrics_store.py
202 lines (178 loc) · 5.95 KB
/
metrics_store.py
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
"""
Metrics collection module
"""
from builtins import str
from ts.metrics.dimension import Dimension
from ts.metrics.metric import Metric
class MetricsStore(object):
"""
DEPRECATED
Class for creating, modifying different metrics. And keep them in a dictionary
"""
def __init__(self, request_ids, model_name):
"""
Initialize metrics map,model name and request map
"""
self.store = list()
self.request_ids = request_ids
self.model_name = model_name
self.cache = {}
def _add_or_update(self, name, value, req_id, unit, metrics_method=None, dimensions=None):
"""
Add a metric key value pair
Parameters
----------
name : str
metric name
value: int, float
value of metric
req_id: str
request id
unit: str
unit of metric
value: int, float , str
value of metric
metrics_method: str, optional
indicates type of metric operation if it is defined
"""
# IF req_id is none error Metric
if dimensions is None:
dimensions = list()
elif not isinstance(dimensions, list):
raise ValueError("Please provide a list of dimensions")
if req_id is None:
dimensions.append(Dimension("Level", "Error"))
else:
dimensions.append(Dimension("ModelName", self.model_name))
dimensions.append(Dimension("Level", "Model"))
# Cache the metric with an unique key for update
dim_str = [name, unit, str(req_id)] + [str(d) for d in dimensions]
dim_str = '-'.join(dim_str)
if dim_str not in self.cache:
metric = Metric(name, value, unit, dimensions, req_id, metrics_method)
self.store.append(metric)
self.cache[dim_str] = metric
else:
self.cache[dim_str].update(value)
def _get_req(self, idx):
"""
Provide the request id dimension
Parameters
----------
idx : int
request_id index in batch
"""
# check if request id for the metric is given, if so use it else have a list of all.
req_id = self.request_ids
if isinstance(req_id, dict):
req_id = ','.join(self.request_ids.values())
if idx is not None and self.request_ids is not None and idx in self.request_ids:
req_id = self.request_ids[idx]
return req_id
def add_counter(self, name, value, idx=None, dimensions=None):
"""
Add a counter metric or increment an existing counter metric
Parameters
----------
name : str
metric name
value: int
value of metric
idx: int
request_id index in batch
dimensions: list
list of dimensions for the metric
"""
unit = 'count'
req_id = self._get_req(idx)
self._add_or_update(name, value, req_id, unit, 'counter', dimensions)
def add_time(self, name, value, idx=None, unit='ms', dimensions=None):
"""
Add a time based metric like latency, default unit is 'ms'
Parameters
----------
name : str
metric name
value: int
value of metric
idx: int
request_id index in batch
unit: str
unit of metric, default here is ms, s is also accepted
dimensions: list
list of dimensions for the metric
"""
if unit not in ['ms', 's']:
raise ValueError("the unit for a timed metric should be one of ['ms', 's']")
req_id = self._get_req(idx)
self._add_or_update(name, value, req_id, unit, dimensions)
def add_size(self, name, value, idx=None, unit='MB', dimensions=None):
"""
Add a size based metric
Parameters
----------
name : str
metric name
value: int, float
value of metric
idx: int
request_id index in batch
unit: str
unit of metric, default here is 'MB', 'kB', 'GB' also supported
dimensions: list
list of dimensions for the metric
"""
if unit not in ['MB', 'kB', 'GB', 'B']:
raise ValueError("The unit for size based metric is one of ['MB','kB', 'GB', 'B']")
req_id = self._get_req(idx)
self._add_or_update(name, value, req_id, unit, dimensions)
def add_percent(self, name, value, idx=None, dimensions=None):
"""
Add a percentage based metric
Parameters
----------
name : str
metric name
value: int, float
value of metric
idx: int
request_id index in batch
dimensions: list
list of dimensions for the metric
"""
unit = 'percent'
req_id = self._get_req(idx)
self._add_or_update(name, value, req_id, unit, dimensions)
def add_error(self, name, value, dimensions=None):
"""
Add a Error Metric
Parameters
----------
name : str
metric name
value: str
value of metric, in this case a str
dimensions: list
list of dimensions for the metric
"""
unit = ''
# noinspection PyTypeChecker
self._add_or_update(name, value, None, unit, dimensions)
def add_metric(self, name, value, unit, idx=None, dimensions=None):
"""
Add a metric which is generic with custom metrics
Parameters
----------
name : str
metric name
value: int, float
value of metric
idx: int
request_id index in batch
unit: str
unit of metric
dimensions: list
list of dimensions for the metric
"""
req_id = self._get_req(idx)
self._add_or_update(name, value, req_id, unit, dimensions)