blob: 64463cf66af1ab2299bd170a79248ecf0191cd80 [file] [log] [blame]
George Keishinge7e91712021-09-03 11:28:44 -05001#!/usr/bin/env python3
Sushil Singh27ef2532021-06-15 23:04:58 -05002
Sushil Singh27ef2532021-06-15 23:04:58 -05003import json
Sushil Singh27ef2532021-06-15 23:04:58 -05004import secrets
5import string
Patrick Williams20f38712022-12-08 06:18:26 -06006import urllib.request
Sushil Singh27ef2532021-06-15 23:04:58 -05007
Patrick Williams20f38712022-12-08 06:18:26 -06008import requests
Sushil Singh27ef2532021-06-15 23:04:58 -05009from robot.api import logger
George Keishinge635ddc2022-12-08 07:38:02 -060010from robot.api.deco import keyword
Patrick Williams20f38712022-12-08 06:18:26 -060011from robot.libraries.BuiltIn import BuiltIn
12from urllib3.exceptions import InsecureRequestWarning
Sushil Singh27ef2532021-06-15 23:04:58 -050013
14
15class redfish_request(object):
Sushil Singh27ef2532021-06-15 23:04:58 -050016 @staticmethod
17 def generate_clientid():
18 r"""
19 Generate 10 character unique id.
20
21 e.g. "oMBhLv2Q9e"
22
23 """
24
Patrick Williams20f38712022-12-08 06:18:26 -060025 clientid = "".join(
26 secrets.choice(string.ascii_letters + string.digits)
27 for i in range(10)
28 )
29 clientid = "".join(str(i) for i in clientid)
Sushil Singh27ef2532021-06-15 23:04:58 -050030
31 return clientid
32
33 @staticmethod
34 def form_url(url):
35 r"""
36 Form a complete path for user url.
37
38 Description of argument(s):
39 url Url passed by user e.g. /redfish/v1/Systems/system.
40 """
41
Patrick Williams20f38712022-12-08 06:18:26 -060042 openbmc_host = BuiltIn().get_variable_value(
43 "${OPENBMC_HOST}", default=""
44 )
Sushil Singh27ef2532021-06-15 23:04:58 -050045 https_port = BuiltIn().get_variable_value("${HTTPS_PORT}", default="")
Patrick Williams20f38712022-12-08 06:18:26 -060046 form_url = (
Sushil Singh27ef2532021-06-15 23:04:58 -050047 "https://" + str(openbmc_host) + ":" + str(https_port) + str(url)
Patrick Williams20f38712022-12-08 06:18:26 -060048 )
Sushil Singh27ef2532021-06-15 23:04:58 -050049
50 return form_url
51
52 @staticmethod
53 def log_console(response):
54 r"""
55 Print function for console.
56
57 Description of argument(s):
58 response Response from requests.
59 """
60
Patrick Williams20f38712022-12-08 06:18:26 -060061 logger.console(msg="", newline=True)
62 logger.info(
63 "Response : [%s]" % response.status_code, also_console=True
64 )
65 logger.console(msg="", newline=True)
Sushil Singh27ef2532021-06-15 23:04:58 -050066
67 def request_login(self, headers, url, credential, timeout=10):
68 r"""
69 Redfish request to create a session.
70
71 Description of argument(s):
72 headers By default headers is assigned as application/json.
73 If user assign the headers,
74 then default headers is not considered.
75 url Requested path from user.
76 credential User has to assign the credential like username and
77 password.
78 UserName = xxxxxxxx Password = xxxxxxxx
79 Client id, user need to assign None in order to auto
80 generate, else user can assign any value.
81 timeout By default timeout is set to 10 seconds.
82 If user assign the timeout, then default timeout
83 value is not considered.
84 """
85
86 if headers == "None":
87 headers = dict()
Patrick Williams20f38712022-12-08 06:18:26 -060088 headers["Content-Type"] = "application/json"
Sushil Singh27ef2532021-06-15 23:04:58 -050089
Patrick Williams20f38712022-12-08 06:18:26 -060090 client_id = credential["Oem"]["OpenBMC"].get("ClientID", "None")
Sushil Singh27ef2532021-06-15 23:04:58 -050091
92 if "None" == client_id:
93 self.clientid = redfish_request.generate_clientid()
Patrick Williams20f38712022-12-08 06:18:26 -060094 credential["Oem"]["OpenBMC"]["ClientID"] = self.clientid
Sushil Singh27ef2532021-06-15 23:04:58 -050095
Patrick Williams20f38712022-12-08 06:18:26 -060096 logger.console(msg="", newline=True)
97 requests.packages.urllib3.disable_warnings(
98 category=InsecureRequestWarning
99 )
100 response = redfish_request.request_post(
101 self, headers=headers, url=url, data=credential
102 )
Sushil Singh27ef2532021-06-15 23:04:58 -0500103
104 return response
105
106 def request_get(self, headers, url, timeout=10, verify=False):
107 r"""
108 Redfish get request.
109
110 Description of argument(s):
111 headers By default headers is assigned as application/json.
112 If user assign the headers, then default headers is not
113 considered.
114 url Requested path from user.
115 timeout By default timeout is set to 10 seconds.
116 If user assign the timeout, then default timeout value
117 is not considered.
118 verify By default verify is set to false means no certificate
119 verification is performed
120 else in case of true, certificate needs to be verified.
121 If user assign the verify, then default verify value
122 is not considered.
123 """
124
Patrick Williams20f38712022-12-08 06:18:26 -0600125 if headers.get("Content-Type", None) is None:
126 headers["Content-Type"] = "application/json"
Sushil Singh27ef2532021-06-15 23:04:58 -0500127
128 url = redfish_request.form_url(url)
129
Patrick Williams20f38712022-12-08 06:18:26 -0600130 logger.console(msg="", newline=True)
131 msg = (
132 "Request Method : GET ,headers = "
133 + json.dumps(headers)
134 + " ,uri = "
135 + str(url)
136 + " ,timeout = "
137 + str(timeout)
138 + " ,verify = "
139 + str(verify)
140 )
Sushil Singh27ef2532021-06-15 23:04:58 -0500141 logger.info(msg, also_console=True)
142
Patrick Williams20f38712022-12-08 06:18:26 -0600143 response = requests.get(
144 url, headers=headers, timeout=timeout, verify=verify
145 )
Sushil Singh27ef2532021-06-15 23:04:58 -0500146 redfish_request.log_console(response)
147
148 return response
149
150 def request_patch(self, headers, url, data=None, timeout=10, verify=False):
151 r"""
152 Redfish patch request.
153
154 Description of argument(s):
155 headers By default headers is assigned as application/json.
156 If user assign the headers, then default headers is not
157 considered.
158 url Requested path from user.
159 data By default data is None.
160 If user assign the data, then default data value is not
161 considered.
162 timeout By default timeout is set to 10 seconds.
163 If user assign the timeout, then default timeout value
164 is not considered.
165 verify By default verify is set to false means no certificate
166 verification is performed
167 else in case of true, certificate needs to be verified.
168 If user assign the verify, then default verify value
169 is not considered.
170 """
171
Patrick Williams20f38712022-12-08 06:18:26 -0600172 if headers.get("Content-Type", None) is None:
173 headers["Content-Type"] = "application/json"
Sushil Singh27ef2532021-06-15 23:04:58 -0500174
175 url = redfish_request.form_url(url)
176
Patrick Williams20f38712022-12-08 06:18:26 -0600177 logger.console(msg="", newline=True)
178 msg = (
179 "Request Method : PATCH ,headers = "
180 + json.dumps(headers)
181 + " ,uri = "
182 + str(url)
183 + " ,data = "
184 + json.dumps(data)
185 + " ,timeout = "
186 + str(timeout)
187 + " ,verify = "
188 + str(verify)
189 )
Sushil Singh27ef2532021-06-15 23:04:58 -0500190 logger.info(msg, also_console=True)
191
Patrick Williams20f38712022-12-08 06:18:26 -0600192 response = requests.patch(
193 url, headers=headers, data=data, timeout=timeout, verify=verify
194 )
Sushil Singh27ef2532021-06-15 23:04:58 -0500195 redfish_request.log_console(response)
196
197 return response
198
199 def request_post(self, headers, url, data=None, timeout=10, verify=False):
200 r"""
201 Redfish post request.
202
203 Description of argument(s):
204 headers By default headers is assigned as application/json.
205 If user assign the headers, then default headers is not
206 considered.
207 url Requested path from user.
208 data By default data is None.
209 If user assign the data, then default data value is not
210 considered.
211 timeout By default timeout is set to 10 seconds.
212 If user assign the timeout, then default timeout value
213 is not considered.
214 verify By default verify is set to false means no
215 certificate verification is performed
216 else in case of true, certificate needs to be verified.
217 If user assign the verify, then default verify value
218 is not considered.
219 """
220
Patrick Williams20f38712022-12-08 06:18:26 -0600221 if headers.get("Content-Type", None) is None:
222 headers["Content-Type"] = "application/json"
Sushil Singh27ef2532021-06-15 23:04:58 -0500223
224 url = redfish_request.form_url(url)
225
Patrick Williams20f38712022-12-08 06:18:26 -0600226 logger.console(msg="", newline=True)
227 msg = (
228 "Request Method : POST ,headers = "
229 + json.dumps(headers)
230 + " ,uri = "
231 + str(url)
232 + " ,data = "
233 + json.dumps(data)
234 + " ,timeout = "
235 + str(timeout)
236 + " ,verify = "
237 + str(verify)
238 )
Sushil Singh27ef2532021-06-15 23:04:58 -0500239 logger.info(msg, also_console=True)
240
Patrick Williams20f38712022-12-08 06:18:26 -0600241 response = requests.post(
242 url,
243 headers=headers,
244 data=json.dumps(data),
245 timeout=timeout,
246 verify=verify,
247 )
Sushil Singh27ef2532021-06-15 23:04:58 -0500248 redfish_request.log_console(response)
249
250 return response
251
Patrick Williams20f38712022-12-08 06:18:26 -0600252 def request_put(
253 self, headers, url, files=None, data=None, timeout=10, verify=False
254 ):
Sushil Singh27ef2532021-06-15 23:04:58 -0500255 r"""
256 Redfish put request.
257
258 Description of argument(s):
259 headers By default headers is assigned as application/json.
260 If user assign the headers, then default headers is not
261 considered.
262 url Requested path from user.
263 files By default files is None.
264 If user assign the files, then default files value
265 is not considered.
266 data By default data is None.
267 If user pass the data, then default data value is not
268 considered.
269 timeout By default timeout is set to 10 seconds.
270 If user pass the timeout, then default timeout value
271 is not considered.
272 verify By default verify is set to false means no
273 certificate verification is performed
274 else in case of true, certificate needs to be verified.
275 If user assign the verify, then default verify value
276 is not considered.
277 """
278
Patrick Williams20f38712022-12-08 06:18:26 -0600279 if headers.get("Content-Type", None) is None:
280 headers["Content-Type"] = "application/json"
Sushil Singh27ef2532021-06-15 23:04:58 -0500281
282 url = redfish_request.form_url(url)
283
Patrick Williams20f38712022-12-08 06:18:26 -0600284 logger.console(msg="", newline=True)
285 msg = (
286 "Request Method : PUT ,headers = "
287 + json.dumps(headers)
288 + " ,uri = "
289 + str(url)
290 + " ,data = "
291 + json.dumps(data)
292 + " ,timeout = "
293 + str(timeout)
294 + " ,verify = "
295 + str(verify)
296 )
Sushil Singh27ef2532021-06-15 23:04:58 -0500297 logger.info(msg, also_console=True)
298
Patrick Williams20f38712022-12-08 06:18:26 -0600299 response = requests.put(
300 url,
301 headers=headers,
302 files=files,
303 data=data,
304 timeout=timeout,
305 verify=verify,
306 )
Sushil Singh27ef2532021-06-15 23:04:58 -0500307 redfish_request.log_console(response)
308
309 return response
310
Patrick Williams20f38712022-12-08 06:18:26 -0600311 def request_delete(
312 self, headers, url, data=None, timeout=10, verify=False
313 ):
Sushil Singh27ef2532021-06-15 23:04:58 -0500314 r"""
315 Redfish delete request.
316
317 Description of argument(s):
318 headers By default headers is assigned as application/json.
319 If user pass the headers then default header is not
320 considered.
321 url Requested path from user.
322 data By default data is None.
323 If user pass the data, then default data value is not
324 considered.
325 timeout By default timeout is set to 10 seconds.
326 If user pass the timeout, then default timeout value
327 is not considered.
328 verify By default verify is set to false means no
329 certificate verification is performed
330 else in case of true, certificate needs to be verified.
331 If user assign the verify, then default verify value
332 is not considered.
333 """
334
Patrick Williams20f38712022-12-08 06:18:26 -0600335 if headers.get("Content-Type", None) is None:
336 headers["Content-Type"] = "application/json"
Sushil Singh27ef2532021-06-15 23:04:58 -0500337
338 url = redfish_request.form_url(url)
339
Patrick Williams20f38712022-12-08 06:18:26 -0600340 logger.console(msg="", newline=True)
341 msg = (
342 "Request Method : DELETE ,headers = "
343 + json.dumps(headers)
344 + " ,uri = "
345 + str(url)
346 + " ,data = "
347 + json.dumps(data)
348 + " ,timeout = "
349 + str(timeout)
350 + " ,verify = "
351 + str(verify)
352 )
353 logger.console(msg="", newline=True)
Sushil Singh27ef2532021-06-15 23:04:58 -0500354
Patrick Williams20f38712022-12-08 06:18:26 -0600355 response = requests.delete(
356 url, headers=headers, data=data, timeout=timeout, verify=verify
357 )
Sushil Singh27ef2532021-06-15 23:04:58 -0500358 redfish_request.log_console(response)
359
360 return response
361
362 @staticmethod
363 def dict_parse(variable, lookup_dict):
364 r"""
365 Find a variable in dict.
366
367 Description of argument(s):
368 variable Variable that need to be searched in dict.
369 lookup_dict Disctionay contains variables.
370 """
371
372 result = lookup_dict.get(variable, None)
373 return result
374
375 @staticmethod
376 def get_target_actions(target_attribute, response):
377 r"""
378 Get target entry of the searched target attribute.
379
380 Description of argument(s):
381 target_attribute Name of the attribute (e.g. 'Manager.Reset').
382 response Response from url.
383
384 'Actions' : {
385 '#Manager.Reset' : {
ganesanb4d430282023-04-27 14:33:23 +0000386 '@Redfish.ActionInfo' : '/redfish/v1/Managers/${MANAGER_ID}/ResetActionInfo',
387 'target' : '/redfish/v1/Managers/${MANAGER_ID}/Actions/Manager.Reset'
Sushil Singh27ef2532021-06-15 23:04:58 -0500388 }
389 }
390 """
391
392 lookup_list = ["Actions", "#" + attribute, "target"]
393 for lookup_item in lookup_list:
394 response = redfish_request.dict_parse(lookup_item, response)
395 if response is not None and type(response) is dict():
396 continue
397 else:
398 return response
399 return None
400
401 @staticmethod
402 def get_attribute(attribute, data):
403 r"""
404 Get resource attribute.
405
406 Description of argument(s):
407 attribute Pass the attribute needs to be searched.
408 data Pass the request response.
409 """
410
411 value = data.get(attribute, None)
412 return value