1 # Copyright (c) 2016 Cisco and/or its affiliates.
2 # Licensed under the Apache License, Version 2.0 (the "License");
3 # you may not use this file except in compliance with the License.
4 # You may obtain a copy of the License at:
6 # http://www.apache.org/licenses/LICENSE-2.0
8 # Unless required by applicable law or agreed to in writing, software
9 # distributed under the License is distributed on an "AS IS" BASIS,
10 # WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
11 # See the License for the specific language governing permissions and
12 # limitations under the License.
14 """Keywords to manipulate bridge domain configuration using Honeycomb REST API.
16 The keywords make possible to put and get configuration data and to get
20 from resources.libraries.python.HTTPRequest import HTTPCodes
21 from resources.libraries.python.honeycomb.HoneycombSetup import HoneycombError
22 from resources.libraries.python.honeycomb.HoneycombUtil \
23 import DataRepresentation
24 from resources.libraries.python.honeycomb.HoneycombUtil \
25 import HoneycombUtil as HcUtil
28 class BridgeDomainKeywords(object):
29 """Keywords to manipulate bridge domain configuration.
31 Implements keywords which get configuration and operational data about
32 bridge domains and put the bridge domains' parameters using Honeycomb REST
36 PARAMS = ("flood", "forward", "learn", "unknown-unicast-flood",
43 def _configure_bd(node, bd_name, data,
44 data_representation=DataRepresentation.JSON):
45 """Send bridge domain configuration data and check the response.
47 :param node: Honeycomb node.
48 :param bd_name: The name of bridge domain.
49 :param data: Configuration data to be sent in PUT request.
50 :param data_representation: How the data is represented.
54 :type data_representation: DataRepresentation
55 :return: Content of response.
57 :raises HoneycombError: If the status code in response on PUT is not
61 status_code, resp = HcUtil.\
62 put_honeycomb_data(node, "config_bridge_domain", data,
63 data_representation=data_representation)
64 if status_code != HTTPCodes.OK:
66 "The configuration of bridge domain '{0}' was not successful. "
67 "Status code: {1}.".format(bd_name, status_code))
71 def _set_bd_properties(node, bd_name, path, new_value=None):
72 """Set bridge domain properties.
74 This method reads bridge domain configuration data, creates, changes or
75 removes the requested data and puts it back to Honeycomb.
77 :param node: Honeycomb node.
78 :param bd_name: The name of bridge domain.
79 :param path: Path to data we want to change, create or remove.
80 :param new_value: The new value to be set. If None, the item will be
85 :type new_value: str, dict or list
86 :return: Content of response.
88 :raises HoneycombError: If it is not possible to get or set the data.
91 status_code, resp = HcUtil.\
92 get_honeycomb_data(node, "config_bridge_domain")
93 if status_code != HTTPCodes.OK:
95 "Not possible to get configuration information about the "
96 "bridge domains. Status code: {0}.".format(status_code))
99 new_data = HcUtil.set_item_value(resp, path, new_value)
101 new_data = HcUtil.remove_item(resp, path)
102 return BridgeDomainKeywords._configure_bd(node, bd_name, new_data)
105 def _create_bd_structure(bd_name, **kwargs):
106 """Create the bridge domain data structure as it is expected by
109 :param bd_name: Bridge domain name.
110 :param kwargs: Parameters and their values. The accepted parameters are
111 defined in BridgeDomainKeywords.PARAMS.
114 :return: Bridge domain data structure.
118 bd_structure = {"name": bd_name}
120 for param, value in kwargs.items():
121 if param not in BridgeDomainKeywords.PARAMS:
122 raise HoneycombError("The parameter {0} is invalid.".
124 bd_structure[param] = str(value)
129 def get_all_bds_cfg_data(node):
130 """Get configuration data about all bridge domains from Honeycomb.
132 :param node: Honeycomb node.
134 :return: Configuration data about all bridge domains from Honeycomb.
136 :raises HoneycombError: If it is not possible to get configuration data.
139 status_code, resp = HcUtil.\
140 get_honeycomb_data(node, "config_bridge_domain")
141 if status_code != HTTPCodes.OK:
142 raise HoneycombError(
143 "Not possible to get configuration information about the "
144 "bridge domains. Status code: {0}.".format(status_code))
146 return resp["bridge-domains"]["bridge-domain"]
148 except (KeyError, TypeError):
152 def get_bd_cfg_data(node, bd_name):
153 """Get configuration data about the given bridge domain from Honeycomb.
155 :param node: Honeycomb node.
156 :param bd_name: The name of bridge domain.
159 :return: Configuration data about the given bridge domain from
164 intfs = BridgeDomainKeywords.get_all_bds_cfg_data(node)
166 if intf["name"] == bd_name:
171 def get_all_bds_oper_data(node):
172 """Get operational data about all bridge domains from Honeycomb.
174 :param node: Honeycomb node.
176 :return: Operational data about all bridge domains from Honeycomb.
178 :raises HoneycombError: If it is not possible to get operational data.
181 status_code, resp = HcUtil.\
182 get_honeycomb_data(node, "oper_bridge_domains")
183 if status_code != HTTPCodes.OK:
184 raise HoneycombError(
185 "Not possible to get operational information about the "
186 "bridge domains. Status code: {0}.".format(status_code))
188 return resp["bridge-domains"]["bridge-domain"]
190 except (KeyError, TypeError):
194 def get_bd_oper_data(node, bd_name):
195 """Get operational data about the given bridge domain from Honeycomb.
197 :param node: Honeycomb node.
198 :param bd_name: The name of bridge domain.
201 :return: Operational data about the given bridge domain from Honeycomb.
205 intfs = BridgeDomainKeywords.get_all_bds_oper_data(node)
207 if intf["name"] == bd_name:
212 def add_first_bd(node, bd_name, **kwargs):
213 """Add the first bridge domain.
215 If there are any other bridge domains configured, they will be removed.
217 :param node: Honeycomb node.
218 :param bd_name: Bridge domain name.
219 :param kwargs: Parameters and their values. The accepted parameters are
220 defined in BridgeDomainKeywords.PARAMS
224 :return: Bridge domain data structure.
228 path = ("bridge-domains", )
229 new_bd = BridgeDomainKeywords._create_bd_structure(bd_name, **kwargs)
230 bridge_domain = {"bridge-domain": [new_bd, ]}
231 return BridgeDomainKeywords._set_bd_properties(node, bd_name, path,
235 def add_bd(node, bd_name, **kwargs):
236 """Add a bridge domain.
238 :param node: Honeycomb node.
239 :param bd_name: Bridge domain name.
240 :param kwargs: Parameters and their values. The accepted parameters are
241 defined in BridgeDomainKeywords.PARAMS
245 :return: Bridge domain data structure.
249 path = ("bridge-domains", "bridge-domain")
250 new_bd = BridgeDomainKeywords._create_bd_structure(bd_name, **kwargs)
251 bridge_domain = [new_bd, ]
252 return BridgeDomainKeywords._set_bd_properties(node, bd_name, path,
256 def remove_all_bds(node):
257 """Remove all bridge domains.
259 :param node: Honeycomb node.
261 :return: Content of response.
263 :raises HoneycombError: If it is not possible to remove all bridge
267 data = {"bridge-domains": {"bridge-domain": []}}
268 status_code, resp = HcUtil.\
269 put_honeycomb_data(node, "config_bridge_domain", data)
270 if status_code != HTTPCodes.OK:
271 raise HoneycombError("Not possible to remove all bridge domains. "
272 "Status code: {0}.".format(status_code))
276 def remove_bridge_domain(node, bd_name):
277 """Remove a bridge domain.
279 :param node: Honeycomb node.
280 :param bd_name: The name of bridge domain to be removed.
283 :return: Content of response.
285 :raises HoneycombError:If it is not possible to remove the bridge
289 path = ("bridge-domains", ("bridge-domain", "name", bd_name))
291 status_code, resp = HcUtil.\
292 get_honeycomb_data(node, "config_bridge_domain")
293 if status_code != HTTPCodes.OK:
294 raise HoneycombError(
295 "Not possible to get configuration information about the "
296 "bridge domains. Status code: {0}.".format(status_code))
298 new_data = HcUtil.remove_item(resp, path)
299 status_code, resp = HcUtil.\
300 put_honeycomb_data(node, "config_bridge_domain", new_data)
301 if status_code != HTTPCodes.OK:
302 raise HoneycombError("Not possible to remove bridge domain {0}. "
304 format(bd_name, status_code))
308 def configure_bridge_domain(node, bd_name, param, value):
309 """Configure a bridge domain.
311 :param node: Honeycomb node.
312 :param bd_name: Bridge domain name.
313 :param param: Parameter to set, change or remove. The accepted
314 parameters are defined in BridgeDomainKeywords.PARAMS
315 :param value: The new value to be set, change or remove. If None, the
316 item will be removed.
321 :return: Content of response.
325 if param not in BridgeDomainKeywords.PARAMS:
326 raise HoneycombError("The parameter {0} is invalid.".format(param))
328 path = ("bridge-domains", ("bridge-domain", "name", bd_name), param)
329 return BridgeDomainKeywords.\
330 _set_bd_properties(node, bd_name, path, value)