4 # Copyright 2017 RIFT.IO Inc
6 # Licensed under the Apache License, Version 2.0 (the "License");
7 # you may not use this file except in compliance with the License.
8 # You may obtain a copy of the License at
10 # http://www.apache.org/licenses/LICENSE-2.0
12 # Unless required by applicable law or agreed to in writing, software
13 # distributed under the License is distributed on an "AS IS" BASIS,
14 # WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
15 # See the License for the specific language governing permissions and
16 # limitations under the License.
21 from ceilometerclient
import client
as ceclient
24 class CeilometerAPIVersionException(Exception):
25 def __init__(self
, errors
):
27 super(CeilometerAPIVersionException
, self
).__init
__("Multiple Exception Received")
30 return self
.__repr
__()
33 msg
= "{} : Following Exception(s) have occured during Neutron API discovery".format(self
.__class
__)
34 for n
,e
in enumerate(self
.errors
):
36 msg
+= " {}: {}".format(n
, str(e
))
39 class CeilometerDriver(object):
41 CeilometerDriver Class for image management
43 ### List of supported API versions in prioritized order
44 supported_versions
= ["2"]
48 region_name
= 'RegionOne',
49 service_type
= 'metering',
52 Constructor for CeilometerDriver class
54 sess_handle (instance of class SessionDriver)
55 region_name (string ): Region name
56 service_type(string) : Service type name
57 logger (instance of logging.Logger)
61 self
.log
= logging
.getLogger('rwcal.openstack.ceilometer')
62 logger
.setLevel(logging
.DEBUG
)
66 self
._sess
_handle
= sess_handle
67 #### Attempt to use API versions in prioritized order defined in
68 #### CeilometerDriver.supported_versions
69 def select_version(version
):
71 self
.log
.info("Attempting to use Ceilometer v%s APIs", version
)
72 cedrv
= ceclient
.Client(version
=version
,
73 region_name
= region_name
,
74 service_type
= service_type
,
75 session
=self
._sess
_handle
.session
)
76 except Exception as e
:
80 self
.log
.info("Ceilometer API v%s selected", version
)
81 return (version
, cedrv
)
84 for v
in CeilometerDriver
.supported_versions
:
86 (self
._version
, self
._ce
_drv
) = select_version(v
)
87 except Exception as e
:
92 raise CeilometerAPIVersionException(errors
)
95 def ceilometer_endpoint(self
):
96 return self
._ce
_drv
.http_client
.get_endpoint()
98 def _get_ceilometer_connection(self
):
100 Returns instance of object ceilometerclient.client.Client
108 Returns instance of object ceilometerclient.client.Client
115 """A list of the available meters"""
117 return self
.client
.meters
.list()
118 except Exception as e
:
119 self
.log
.exception("List meters operation failed. Exception: %s", str(e
))
124 """The ceilometer client alarms manager"""
125 return self
.client
.alarms
127 def nfvi_metrics(self
, vim_id
):
128 """Returns a dict of NFVI metrics for a given VM
131 vim_id - the VIM ID of the VM to retrieve the metrics for
134 A dict of NFVI metrics
137 def query_latest_sample(counter_name
):
139 filter = json
.dumps({
141 {"=": {"resource": vim_id
}},
142 {"=": {"counter_name": counter_name
}}
145 orderby
= json
.dumps([{"timestamp": "DESC"}])
146 result
= self
.client
.query_samples
.query(filter=filter,
154 except Exception as e
:
155 self
.log
.exception("Got exception while querying ceilometer, exception details:%s", str(e
))
159 memory_usage
= query_latest_sample("memory.usage")
160 disk_usage
= query_latest_sample("disk.usage")
161 cpu_util
= query_latest_sample("cpu_util")
165 if memory_usage
is not None:
166 memory_usage
.volume
= 1e6
* memory_usage
.volume
167 metrics
["memory_usage"] = memory_usage
.to_dict()
169 if disk_usage
is not None:
170 metrics
["disk_usage"] = disk_usage
.to_dict()
172 if cpu_util
is not None:
173 metrics
["cpu_util"] = cpu_util
.to_dict()
174 # RIFT-14041 when ceilometer returns value of more than 100, make it 100
175 if metrics
["cpu_util"]["volume"] > 100:
176 metrics
["cpu_util"]["volume"] = 100
180 def query_samples(self
, vim_instance_id
, counter_name
, limit
=1):
181 """Returns a list of samples
184 vim_instance_id - the ID of the VIM that the samples are from
185 counter_name - the counter that the samples will come from
186 limit - a limit on the number of samples to return
194 filter = json
.dumps({
196 {"=": {"resource": vim_instance_id
}},
197 {"=": {"counter_name": counter_name
}}
201 result
= self
.client
.query_samples
.query(filter=filter, limit
=limit
)
202 except Exception as e
:
203 self
.log
.exception("Query samples operation failed. Exception: %s",str(e
))
204 return result
[-limit
:]
206 except Exception as e
:
207 self
.log
.exception(e
)