blob: 0035b118f78472dcc4499f676806677aceff645b [file] [log] [blame]
George Liua7210022022-10-05 15:44:11 +08001#pragma once
2
3#include "app.hpp"
4#include "dbus_utility.hpp"
5#include "query.hpp"
6#include "registries/privilege_registry.hpp"
7#include "utils/chassis_utils.hpp"
George Liu2b45fb32022-10-05 17:00:00 +08008#include "utils/dbus_utils.hpp"
9#include "utils/json_utils.hpp"
George Liua7210022022-10-05 15:44:11 +080010
George Liu34dfcb92022-10-05 16:47:44 +080011#include <boost/system/error_code.hpp>
Ed Tanousef4c65b2023-04-24 15:28:50 -070012#include <boost/url/format.hpp>
13
George Liua7210022022-10-05 15:44:11 +080014#include <memory>
15#include <optional>
16#include <string>
17
18namespace redfish
19{
20
Lakshmi Yadlapati788fe6c2023-06-21 14:39:08 -050021static constexpr std::array<std::string_view, 1> powerSupplyInterface = {
22 "xyz.openbmc_project.Inventory.Item.PowerSupply"};
23
24inline void updatePowerSupplyList(
25 const std::shared_ptr<bmcweb::AsyncResp>& asyncResp,
26 const std::string& chassisId,
27 const dbus::utility::MapperGetSubTreePathsResponse& powerSupplyPaths)
George Liua7210022022-10-05 15:44:11 +080028{
George Liu00ef5dc2022-10-05 16:27:52 +080029 nlohmann::json& powerSupplyList = asyncResp->res.jsonValue["Members"];
Lakshmi Yadlapati788fe6c2023-06-21 14:39:08 -050030 for (const std::string& powerSupplyPath : powerSupplyPaths)
31 {
32 std::string powerSupplyName =
33 sdbusplus::message::object_path(powerSupplyPath).filename();
34 if (powerSupplyName.empty())
35 {
36 continue;
37 }
38
39 nlohmann::json item = nlohmann::json::object();
40 item["@odata.id"] = boost::urls::format(
41 "/redfish/v1/Chassis/{}/PowerSubsystem/PowerSupplies/{}", chassisId,
42 powerSupplyName);
43
44 powerSupplyList.emplace_back(std::move(item));
45 }
George Liu00ef5dc2022-10-05 16:27:52 +080046 asyncResp->res.jsonValue["Members@odata.count"] = powerSupplyList.size();
George Liua7210022022-10-05 15:44:11 +080047}
48
49inline void
50 doPowerSupplyCollection(const std::shared_ptr<bmcweb::AsyncResp>& asyncResp,
51 const std::string& chassisId,
52 const std::optional<std::string>& validChassisPath)
53{
54 if (!validChassisPath)
55 {
56 messages::resourceNotFound(asyncResp->res, "Chassis", chassisId);
57 return;
58 }
59
60 asyncResp->res.addHeader(
61 boost::beast::http::field::link,
62 "</redfish/v1/JsonSchemas/PowerSupplyCollection/PowerSupplyCollection.json>; rel=describedby");
63 asyncResp->res.jsonValue["@odata.type"] =
64 "#PowerSupplyCollection.PowerSupplyCollection";
65 asyncResp->res.jsonValue["Name"] = "Power Supply Collection";
Ed Tanousef4c65b2023-04-24 15:28:50 -070066 asyncResp->res.jsonValue["@odata.id"] = boost::urls::format(
67 "/redfish/v1/Chassis/{}/PowerSubsystem/PowerSupplies", chassisId);
George Liua7210022022-10-05 15:44:11 +080068 asyncResp->res.jsonValue["Description"] =
69 "The collection of PowerSupply resource instances.";
George Liu7a2bb2c2023-04-11 10:44:33 +080070 asyncResp->res.jsonValue["Members"] = nlohmann::json::array();
71 asyncResp->res.jsonValue["Members@odata.count"] = 0;
George Liua7210022022-10-05 15:44:11 +080072
73 std::string powerPath = *validChassisPath + "/powered_by";
Lakshmi Yadlapati788fe6c2023-06-21 14:39:08 -050074 dbus::utility::getAssociatedSubTreePaths(
75 powerPath,
76 sdbusplus::message::object_path("/xyz/openbmc_project/inventory"), 0,
77 powerSupplyInterface,
78 [asyncResp, chassisId](
79 const boost::system::error_code& ec,
80 const dbus::utility::MapperGetSubTreePathsResponse& subtreePaths) {
81 if (ec)
82 {
83 if (ec.value() != EBADR)
George Liua7210022022-10-05 15:44:11 +080084 {
Ed Tanous62598e32023-07-17 17:06:25 -070085 BMCWEB_LOG_ERROR("DBUS response error{}", ec.value());
Lakshmi Yadlapati788fe6c2023-06-21 14:39:08 -050086 messages::internalError(asyncResp->res);
George Liua7210022022-10-05 15:44:11 +080087 }
Lakshmi Yadlapati788fe6c2023-06-21 14:39:08 -050088 return;
89 }
George Liua7210022022-10-05 15:44:11 +080090
Lakshmi Yadlapati788fe6c2023-06-21 14:39:08 -050091 updatePowerSupplyList(asyncResp, chassisId, subtreePaths);
George Liua7210022022-10-05 15:44:11 +080092 });
93}
94
95inline void handlePowerSupplyCollectionHead(
96 App& app, const crow::Request& req,
97 const std::shared_ptr<bmcweb::AsyncResp>& asyncResp,
98 const std::string& chassisId)
99{
100 if (!redfish::setUpRedfishRoute(app, req, asyncResp))
101 {
102 return;
103 }
104
105 redfish::chassis_utils::getValidChassisPath(
106 asyncResp, chassisId,
107 [asyncResp,
108 chassisId](const std::optional<std::string>& validChassisPath) {
109 if (!validChassisPath)
110 {
111 messages::resourceNotFound(asyncResp->res, "Chassis", chassisId);
112 return;
113 }
114 asyncResp->res.addHeader(
115 boost::beast::http::field::link,
116 "</redfish/v1/JsonSchemas/PowerSupplyCollection/PowerSupplyCollection.json>; rel=describedby");
117 });
118}
119
120inline void handlePowerSupplyCollectionGet(
121 App& app, const crow::Request& req,
122 const std::shared_ptr<bmcweb::AsyncResp>& asyncResp,
123 const std::string& chassisId)
124{
125 if (!redfish::setUpRedfishRoute(app, req, asyncResp))
126 {
127 return;
128 }
129
130 redfish::chassis_utils::getValidChassisPath(
131 asyncResp, chassisId,
132 std::bind_front(doPowerSupplyCollection, asyncResp, chassisId));
133}
134
135inline void requestRoutesPowerSupplyCollection(App& app)
136{
137 BMCWEB_ROUTE(app, "/redfish/v1/Chassis/<str>/PowerSubsystem/PowerSupplies/")
138 .privileges(redfish::privileges::headPowerSupplyCollection)
139 .methods(boost::beast::http::verb::head)(
140 std::bind_front(handlePowerSupplyCollectionHead, std::ref(app)));
141
142 BMCWEB_ROUTE(app, "/redfish/v1/Chassis/<str>/PowerSubsystem/PowerSupplies/")
143 .privileges(redfish::privileges::getPowerSupplyCollection)
144 .methods(boost::beast::http::verb::get)(
145 std::bind_front(handlePowerSupplyCollectionGet, std::ref(app)));
146}
147
George Liu00ef5dc2022-10-05 16:27:52 +0800148inline bool checkPowerSupplyId(const std::string& powerSupplyPath,
149 const std::string& powerSupplyId)
150{
151 std::string powerSupplyName =
152 sdbusplus::message::object_path(powerSupplyPath).filename();
153
154 return !(powerSupplyName.empty() || powerSupplyName != powerSupplyId);
155}
156
George Liu34dfcb92022-10-05 16:47:44 +0800157inline void getValidPowerSupplyPath(
158 const std::shared_ptr<bmcweb::AsyncResp>& asyncResp,
159 const std::string& validChassisPath, const std::string& powerSupplyId,
160 std::function<void(const std::string& powerSupplyPath)>&& callback)
George Liu00ef5dc2022-10-05 16:27:52 +0800161{
162 std::string powerPath = validChassisPath + "/powered_by";
Lakshmi Yadlapati788fe6c2023-06-21 14:39:08 -0500163 dbus::utility::getAssociatedSubTreePaths(
164 powerPath,
165 sdbusplus::message::object_path("/xyz/openbmc_project/inventory"), 0,
166 powerSupplyInterface,
167 [asyncResp, powerSupplyId, callback{std::move(callback)}](
168 const boost::system::error_code& ec,
169 const dbus::utility::MapperGetSubTreePathsResponse& subtreePaths) {
170 if (ec)
171 {
172 if (ec.value() != EBADR)
George Liu00ef5dc2022-10-05 16:27:52 +0800173 {
Ed Tanous62598e32023-07-17 17:06:25 -0700174 BMCWEB_LOG_ERROR(
175 "DBUS response error for getAssociatedSubTreePaths{}",
176 ec.value());
Lakshmi Yadlapati788fe6c2023-06-21 14:39:08 -0500177 messages::internalError(asyncResp->res);
George Liu00ef5dc2022-10-05 16:27:52 +0800178 return;
179 }
Lakshmi Yadlapati788fe6c2023-06-21 14:39:08 -0500180 messages::resourceNotFound(asyncResp->res, "PowerSupplies",
181 powerSupplyId);
182 return;
183 }
George Liu00ef5dc2022-10-05 16:27:52 +0800184
Lakshmi Yadlapati788fe6c2023-06-21 14:39:08 -0500185 for (const std::string& path : subtreePaths)
186 {
187 if (checkPowerSupplyId(path, powerSupplyId))
George Liu00ef5dc2022-10-05 16:27:52 +0800188 {
Lakshmi Yadlapati788fe6c2023-06-21 14:39:08 -0500189 callback(path);
George Liu00ef5dc2022-10-05 16:27:52 +0800190 return;
191 }
Lakshmi Yadlapati788fe6c2023-06-21 14:39:08 -0500192 }
193
194 if (!subtreePaths.empty())
195 {
Ed Tanous62598e32023-07-17 17:06:25 -0700196 BMCWEB_LOG_WARNING("Power supply not found: {}", powerSupplyId);
Lakshmi Yadlapati788fe6c2023-06-21 14:39:08 -0500197 messages::resourceNotFound(asyncResp->res, "PowerSupplies",
198 powerSupplyId);
199 return;
200 }
George Liu00ef5dc2022-10-05 16:27:52 +0800201 });
202}
203
204inline void
George Liu34dfcb92022-10-05 16:47:44 +0800205 getPowerSupplyState(const std::shared_ptr<bmcweb::AsyncResp>& asyncResp,
206 const std::string& service, const std::string& path)
207{
208 sdbusplus::asio::getProperty<bool>(
209 *crow::connections::systemBus, service, path,
210 "xyz.openbmc_project.Inventory.Item", "Present",
211 [asyncResp](const boost::system::error_code& ec, const bool value) {
212 if (ec)
213 {
214 if (ec.value() != EBADR)
215 {
Ed Tanous62598e32023-07-17 17:06:25 -0700216 BMCWEB_LOG_ERROR("DBUS response error for State {}",
217 ec.value());
George Liu34dfcb92022-10-05 16:47:44 +0800218 messages::internalError(asyncResp->res);
219 }
220 return;
221 }
222
223 if (!value)
224 {
225 asyncResp->res.jsonValue["Status"]["State"] = "Absent";
226 }
227 });
228}
229
230inline void
231 getPowerSupplyHealth(const std::shared_ptr<bmcweb::AsyncResp>& asyncResp,
232 const std::string& service, const std::string& path)
233{
234 sdbusplus::asio::getProperty<bool>(
235 *crow::connections::systemBus, service, path,
236 "xyz.openbmc_project.State.Decorator.OperationalStatus", "Functional",
237 [asyncResp](const boost::system::error_code& ec, const bool value) {
238 if (ec)
239 {
240 if (ec.value() != EBADR)
241 {
Ed Tanous62598e32023-07-17 17:06:25 -0700242 BMCWEB_LOG_ERROR("DBUS response error for Health {}",
243 ec.value());
George Liu34dfcb92022-10-05 16:47:44 +0800244 messages::internalError(asyncResp->res);
245 }
246 return;
247 }
248
249 if (!value)
250 {
251 asyncResp->res.jsonValue["Status"]["Health"] = "Critical";
252 }
253 });
254}
255
256inline void
George Liu2b45fb32022-10-05 17:00:00 +0800257 getPowerSupplyAsset(const std::shared_ptr<bmcweb::AsyncResp>& asyncResp,
258 const std::string& service, const std::string& path)
259{
260 sdbusplus::asio::getAllProperties(
261 *crow::connections::systemBus, service, path,
262 "xyz.openbmc_project.Inventory.Decorator.Asset",
263 [asyncResp](const boost::system::error_code& ec,
264 const dbus::utility::DBusPropertiesMap& propertiesList) {
265 if (ec)
266 {
267 if (ec.value() != EBADR)
268 {
Ed Tanous62598e32023-07-17 17:06:25 -0700269 BMCWEB_LOG_ERROR("DBUS response error for Asset {}",
270 ec.value());
George Liu2b45fb32022-10-05 17:00:00 +0800271 messages::internalError(asyncResp->res);
272 }
273 return;
274 }
275
276 const std::string* partNumber = nullptr;
277 const std::string* serialNumber = nullptr;
278 const std::string* manufacturer = nullptr;
279 const std::string* model = nullptr;
280 const std::string* sparePartNumber = nullptr;
281
282 const bool success = sdbusplus::unpackPropertiesNoThrow(
283 dbus_utils::UnpackErrorPrinter(), propertiesList, "PartNumber",
284 partNumber, "SerialNumber", serialNumber, "Manufacturer",
285 manufacturer, "Model", model, "SparePartNumber", sparePartNumber);
286
287 if (!success)
288 {
289 messages::internalError(asyncResp->res);
290 return;
291 }
292
293 if (partNumber != nullptr)
294 {
295 asyncResp->res.jsonValue["PartNumber"] = *partNumber;
296 }
297
298 if (serialNumber != nullptr)
299 {
300 asyncResp->res.jsonValue["SerialNumber"] = *serialNumber;
301 }
302
303 if (manufacturer != nullptr)
304 {
305 asyncResp->res.jsonValue["Manufacturer"] = *manufacturer;
306 }
307
308 if (model != nullptr)
309 {
310 asyncResp->res.jsonValue["Model"] = *model;
311 }
312
313 // SparePartNumber is optional on D-Bus so skip if it is empty
314 if (sparePartNumber != nullptr && !sparePartNumber->empty())
315 {
316 asyncResp->res.jsonValue["SparePartNumber"] = *sparePartNumber;
317 }
318 });
319}
320
George Liua0dba872022-10-05 17:03:20 +0800321inline void getPowerSupplyFirmwareVersion(
322 const std::shared_ptr<bmcweb::AsyncResp>& asyncResp,
323 const std::string& service, const std::string& path)
324{
325 sdbusplus::asio::getProperty<std::string>(
326 *crow::connections::systemBus, service, path,
327 "xyz.openbmc_project.Software.Version", "Version",
328 [asyncResp](const boost::system::error_code& ec,
329 const std::string& value) {
330 if (ec)
331 {
332 if (ec.value() != EBADR)
333 {
Ed Tanous62598e32023-07-17 17:06:25 -0700334 BMCWEB_LOG_ERROR("DBUS response error for FirmwareVersion {}",
335 ec.value());
George Liua0dba872022-10-05 17:03:20 +0800336 messages::internalError(asyncResp->res);
337 }
338 return;
339 }
340 asyncResp->res.jsonValue["FirmwareVersion"] = value;
341 });
342}
343
George Liu2b45fb32022-10-05 17:00:00 +0800344inline void
George Liu44845e52022-10-05 17:09:21 +0800345 getPowerSupplyLocation(const std::shared_ptr<bmcweb::AsyncResp>& asyncResp,
346 const std::string& service, const std::string& path)
347{
348 sdbusplus::asio::getProperty<std::string>(
349 *crow::connections::systemBus, service, path,
350 "xyz.openbmc_project.Inventory.Decorator.LocationCode", "LocationCode",
351 [asyncResp](const boost::system::error_code& ec,
352 const std::string& value) {
353 if (ec)
354 {
355 if (ec.value() != EBADR)
356 {
Ed Tanous62598e32023-07-17 17:06:25 -0700357 BMCWEB_LOG_ERROR("DBUS response error for Location {}",
358 ec.value());
George Liu44845e52022-10-05 17:09:21 +0800359 messages::internalError(asyncResp->res);
360 }
361 return;
362 }
363 asyncResp->res.jsonValue["Location"]["PartLocation"]["ServiceLabel"] =
364 value;
365 });
366}
367
George Liuddceee02022-10-06 08:57:11 +0800368inline void handleGetEfficiencyResponse(
369 const std::shared_ptr<bmcweb::AsyncResp>& asyncResp,
370 const boost::system::error_code& ec, uint32_t value)
371{
372 if (ec)
373 {
374 if (ec.value() != EBADR)
375 {
Ed Tanous62598e32023-07-17 17:06:25 -0700376 BMCWEB_LOG_ERROR("DBUS response error for DeratingFactor {}",
377 ec.value());
George Liuddceee02022-10-06 08:57:11 +0800378 messages::internalError(asyncResp->res);
379 }
380 return;
381 }
382 // The PDI default value is 0, if it hasn't been set leave off
383 if (value == 0)
384 {
385 return;
386 }
387
388 nlohmann::json::array_t efficiencyRatings;
389 nlohmann::json::object_t efficiencyPercent;
390 efficiencyPercent["EfficiencyPercent"] = value;
391 efficiencyRatings.emplace_back(std::move(efficiencyPercent));
392 asyncResp->res.jsonValue["EfficiencyRatings"] =
393 std::move(efficiencyRatings);
394}
395
396inline void handlePowerSupplyAttributesSubTreeResponse(
397 const std::shared_ptr<bmcweb::AsyncResp>& asyncResp,
398 const boost::system::error_code& ec,
399 const dbus::utility::MapperGetSubTreeResponse& subtree)
400{
401 if (ec)
402 {
403 if (ec.value() != EBADR)
404 {
Ed Tanous62598e32023-07-17 17:06:25 -0700405 BMCWEB_LOG_ERROR("DBUS response error for EfficiencyPercent {}",
406 ec.value());
George Liuddceee02022-10-06 08:57:11 +0800407 messages::internalError(asyncResp->res);
408 }
409 return;
410 }
411
412 if (subtree.empty())
413 {
Ed Tanous62598e32023-07-17 17:06:25 -0700414 BMCWEB_LOG_DEBUG("Can't find Power Supply Attributes!");
George Liuddceee02022-10-06 08:57:11 +0800415 return;
416 }
417
418 if (subtree.size() != 1)
419 {
Ed Tanous62598e32023-07-17 17:06:25 -0700420 BMCWEB_LOG_ERROR(
421 "Unexpected number of paths returned by getSubTree: {}",
422 subtree.size());
George Liuddceee02022-10-06 08:57:11 +0800423 messages::internalError(asyncResp->res);
424 return;
425 }
426
427 const auto& [path, serviceMap] = *subtree.begin();
428 const auto& [service, interfaces] = *serviceMap.begin();
429 sdbusplus::asio::getProperty<uint32_t>(
430 *crow::connections::systemBus, service, path,
431 "xyz.openbmc_project.Control.PowerSupplyAttributes", "DeratingFactor",
432 [asyncResp](const boost::system::error_code& ec1, uint32_t value) {
433 handleGetEfficiencyResponse(asyncResp, ec1, value);
434 });
435}
436
437inline void
438 getEfficiencyPercent(const std::shared_ptr<bmcweb::AsyncResp>& asyncResp)
439{
440 constexpr std::array<std::string_view, 1> efficiencyIntf = {
441 "xyz.openbmc_project.Control.PowerSupplyAttributes"};
442
443 dbus::utility::getSubTree(
444 "/xyz/openbmc_project", 0, efficiencyIntf,
445 [asyncResp](const boost::system::error_code& ec,
446 const dbus::utility::MapperGetSubTreeResponse& subtree) {
447 handlePowerSupplyAttributesSubTreeResponse(asyncResp, ec, subtree);
448 });
449}
450
George Liu44845e52022-10-05 17:09:21 +0800451inline void
George Liu00ef5dc2022-10-05 16:27:52 +0800452 doPowerSupplyGet(const std::shared_ptr<bmcweb::AsyncResp>& asyncResp,
453 const std::string& chassisId,
454 const std::string& powerSupplyId,
455 const std::optional<std::string>& validChassisPath)
456{
457 if (!validChassisPath)
458 {
459 messages::resourceNotFound(asyncResp->res, "Chassis", chassisId);
460 return;
461 }
462
463 // Get the correct Path and Service that match the input parameters
464 getValidPowerSupplyPath(asyncResp, *validChassisPath, powerSupplyId,
George Liu34dfcb92022-10-05 16:47:44 +0800465 [asyncResp, chassisId, powerSupplyId](
466 const std::string& powerSupplyPath) {
George Liu00ef5dc2022-10-05 16:27:52 +0800467 asyncResp->res.addHeader(
468 boost::beast::http::field::link,
469 "</redfish/v1/JsonSchemas/PowerSupply/PowerSupply.json>; rel=describedby");
470 asyncResp->res.jsonValue["@odata.type"] =
471 "#PowerSupply.v1_5_0.PowerSupply";
472 asyncResp->res.jsonValue["Name"] = "Power Supply";
473 asyncResp->res.jsonValue["Id"] = powerSupplyId;
474 asyncResp->res.jsonValue["@odata.id"] = boost::urls::format(
475 "/redfish/v1/Chassis/{}/PowerSubsystem/PowerSupplies/{}", chassisId,
476 powerSupplyId);
George Liu34dfcb92022-10-05 16:47:44 +0800477
478 asyncResp->res.jsonValue["Status"]["State"] = "Enabled";
479 asyncResp->res.jsonValue["Status"]["Health"] = "OK";
480
George Liu34dfcb92022-10-05 16:47:44 +0800481 dbus::utility::getDbusObject(
Lakshmi Yadlapati788fe6c2023-06-21 14:39:08 -0500482 powerSupplyPath, powerSupplyInterface,
George Liu34dfcb92022-10-05 16:47:44 +0800483 [asyncResp,
484 powerSupplyPath](const boost::system::error_code& ec,
485 const dbus::utility::MapperGetObject& object) {
486 if (ec || object.empty())
487 {
488 messages::internalError(asyncResp->res);
489 return;
490 }
491
492 getPowerSupplyState(asyncResp, object.begin()->first,
493 powerSupplyPath);
494 getPowerSupplyHealth(asyncResp, object.begin()->first,
495 powerSupplyPath);
George Liu2b45fb32022-10-05 17:00:00 +0800496 getPowerSupplyAsset(asyncResp, object.begin()->first,
497 powerSupplyPath);
George Liua0dba872022-10-05 17:03:20 +0800498 getPowerSupplyFirmwareVersion(asyncResp, object.begin()->first,
499 powerSupplyPath);
George Liu44845e52022-10-05 17:09:21 +0800500 getPowerSupplyLocation(asyncResp, object.begin()->first,
501 powerSupplyPath);
George Liu34dfcb92022-10-05 16:47:44 +0800502 });
George Liuddceee02022-10-06 08:57:11 +0800503
504 getEfficiencyPercent(asyncResp);
George Liu00ef5dc2022-10-05 16:27:52 +0800505 });
506}
507
508inline void
509 handlePowerSupplyHead(App& app, const crow::Request& req,
510 const std::shared_ptr<bmcweb::AsyncResp>& asyncResp,
511 const std::string& chassisId,
512 const std::string& powerSupplyId)
513{
514 if (!redfish::setUpRedfishRoute(app, req, asyncResp))
515 {
516 return;
517 }
518
519 redfish::chassis_utils::getValidChassisPath(
520 asyncResp, chassisId,
521 [asyncResp, chassisId,
522 powerSupplyId](const std::optional<std::string>& validChassisPath) {
523 if (!validChassisPath)
524 {
525 messages::resourceNotFound(asyncResp->res, "Chassis", chassisId);
526 return;
527 }
528
529 // Get the correct Path and Service that match the input parameters
530 getValidPowerSupplyPath(asyncResp, *validChassisPath, powerSupplyId,
George Liu34dfcb92022-10-05 16:47:44 +0800531 [asyncResp](const std::string&) {
George Liu00ef5dc2022-10-05 16:27:52 +0800532 asyncResp->res.addHeader(
533 boost::beast::http::field::link,
534 "</redfish/v1/JsonSchemas/PowerSupply/PowerSupply.json>; rel=describedby");
535 });
536 });
537}
538
539inline void
540 handlePowerSupplyGet(App& app, const crow::Request& req,
541 const std::shared_ptr<bmcweb::AsyncResp>& asyncResp,
542 const std::string& chassisId,
543 const std::string& powerSupplyId)
544{
545 if (!redfish::setUpRedfishRoute(app, req, asyncResp))
546 {
547 return;
548 }
549
550 redfish::chassis_utils::getValidChassisPath(
551 asyncResp, chassisId,
552 std::bind_front(doPowerSupplyGet, asyncResp, chassisId, powerSupplyId));
553}
554
555inline void requestRoutesPowerSupply(App& app)
556{
557 BMCWEB_ROUTE(
558 app, "/redfish/v1/Chassis/<str>/PowerSubsystem/PowerSupplies/<str>/")
559 .privileges(redfish::privileges::headPowerSupply)
560 .methods(boost::beast::http::verb::head)(
561 std::bind_front(handlePowerSupplyHead, std::ref(app)));
562
563 BMCWEB_ROUTE(
564 app, "/redfish/v1/Chassis/<str>/PowerSubsystem/PowerSupplies/<str>/")
565 .privileges(redfish::privileges::getPowerSupply)
566 .methods(boost::beast::http::verb::get)(
567 std::bind_front(handlePowerSupplyGet, std::ref(app)));
568}
569
George Liua7210022022-10-05 15:44:11 +0800570} // namespace redfish