xref: /openbmc/bmcweb/features/redfish/lib/managers.hpp (revision ca537928fbd8c22736a7cd30c98d5f3640a3523a)
19c310685SBorawski.Lukasz /*
29c310685SBorawski.Lukasz // Copyright (c) 2018 Intel Corporation
39c310685SBorawski.Lukasz //
49c310685SBorawski.Lukasz // Licensed under the Apache License, Version 2.0 (the "License");
59c310685SBorawski.Lukasz // you may not use this file except in compliance with the License.
69c310685SBorawski.Lukasz // You may obtain a copy of the License at
79c310685SBorawski.Lukasz //
89c310685SBorawski.Lukasz //      http://www.apache.org/licenses/LICENSE-2.0
99c310685SBorawski.Lukasz //
109c310685SBorawski.Lukasz // Unless required by applicable law or agreed to in writing, software
119c310685SBorawski.Lukasz // distributed under the License is distributed on an "AS IS" BASIS,
129c310685SBorawski.Lukasz // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
139c310685SBorawski.Lukasz // See the License for the specific language governing permissions and
149c310685SBorawski.Lukasz // limitations under the License.
159c310685SBorawski.Lukasz */
169c310685SBorawski.Lukasz #pragma once
179c310685SBorawski.Lukasz 
189c310685SBorawski.Lukasz #include "node.hpp"
199c310685SBorawski.Lukasz 
201abe55efSEd Tanous namespace redfish
211abe55efSEd Tanous {
229c310685SBorawski.Lukasz 
23*ca537928SJennifer Lee /**
24*ca537928SJennifer Lee  * DBus types primitives for several generic DBus interfaces
25*ca537928SJennifer Lee  * TODO consider move this to separate file into boost::dbus
26*ca537928SJennifer Lee  */
27*ca537928SJennifer Lee using GetManagedObjectsType = boost::container::flat_map<
28*ca537928SJennifer Lee     sdbusplus::message::object_path,
29*ca537928SJennifer Lee     boost::container::flat_map<
30*ca537928SJennifer Lee         std::string,
31*ca537928SJennifer Lee         boost::container::flat_map<
32*ca537928SJennifer Lee             std::string, sdbusplus::message::variant<
33*ca537928SJennifer Lee                              std::string, bool, uint8_t, int16_t, uint16_t,
34*ca537928SJennifer Lee                              int32_t, uint32_t, int64_t, uint64_t, double>>>>;
35*ca537928SJennifer Lee 
361abe55efSEd Tanous class Manager : public Node
371abe55efSEd Tanous {
389c310685SBorawski.Lukasz   public:
391abe55efSEd Tanous     Manager(CrowApp &app) : Node(app, "/redfish/v1/Managers/openbmc/")
401abe55efSEd Tanous     {
419c310685SBorawski.Lukasz         Node::json["@odata.id"] = "/redfish/v1/Managers/openbmc";
429c310685SBorawski.Lukasz         Node::json["@odata.type"] = "#Manager.v1_3_0.Manager";
439c310685SBorawski.Lukasz         Node::json["@odata.context"] = "/redfish/v1/$metadata#Manager.Manager";
449c310685SBorawski.Lukasz         Node::json["Id"] = "openbmc";
459c310685SBorawski.Lukasz         Node::json["Name"] = "OpenBmc Manager";
469c310685SBorawski.Lukasz         Node::json["Description"] = "Baseboard Management Controller";
479c310685SBorawski.Lukasz         Node::json["PowerState"] = "On";
48*ca537928SJennifer Lee         Node::json["ManagerType"] = "BMC";
499c310685SBorawski.Lukasz         Node::json["UUID"] =
5055c7b7a2SEd Tanous             app.template getMiddleware<crow::persistent_data::Middleware>()
5155c7b7a2SEd Tanous                 .systemUuid;
529c310685SBorawski.Lukasz         Node::json["Model"] = "OpenBmc"; // TODO(ed), get model
53*ca537928SJennifer Lee         Node::json["EthernetInterfaces"] = {
54*ca537928SJennifer Lee             {"@odata.id", "/redfish/v1/Managers/openbmc/EthernetInterfaces"}};
553ebd75f7SEd Tanous 
56a434f2bdSEd Tanous         entityPrivileges = {
57a434f2bdSEd Tanous             {boost::beast::http::verb::get, {{"Login"}}},
58e0d918bcSEd Tanous             {boost::beast::http::verb::head, {{"Login"}}},
59e0d918bcSEd Tanous             {boost::beast::http::verb::patch, {{"ConfigureManager"}}},
60e0d918bcSEd Tanous             {boost::beast::http::verb::put, {{"ConfigureManager"}}},
61e0d918bcSEd Tanous             {boost::beast::http::verb::delete_, {{"ConfigureManager"}}},
62e0d918bcSEd Tanous             {boost::beast::http::verb::post, {{"ConfigureManager"}}}};
639c310685SBorawski.Lukasz     }
649c310685SBorawski.Lukasz 
659c310685SBorawski.Lukasz   private:
6655c7b7a2SEd Tanous     void doGet(crow::Response &res, const crow::Request &req,
671abe55efSEd Tanous                const std::vector<std::string> &params) override
681abe55efSEd Tanous     {
69*ca537928SJennifer Lee         std::shared_ptr<AsyncResp> asyncResp = std::make_shared<AsyncResp>(res);
70*ca537928SJennifer Lee         asyncResp->res.jsonValue = Node::json;
71*ca537928SJennifer Lee 
729c310685SBorawski.Lukasz         Node::json["DateTime"] = getDateTime();
7355c7b7a2SEd Tanous         res.jsonValue = Node::json;
74*ca537928SJennifer Lee         crow::connections::systemBus->async_method_call(
75*ca537928SJennifer Lee             [asyncResp](const boost::system::error_code ec,
76*ca537928SJennifer Lee                         const GetManagedObjectsType &resp) {
77*ca537928SJennifer Lee                 if (ec)
78*ca537928SJennifer Lee                 {
79*ca537928SJennifer Lee                     BMCWEB_LOG_ERROR << "Error while getting Software Version";
80*ca537928SJennifer Lee                     asyncResp->res.result(
81*ca537928SJennifer Lee                         boost::beast::http::status::internal_server_error);
82*ca537928SJennifer Lee                     return;
83*ca537928SJennifer Lee                 }
84*ca537928SJennifer Lee 
85*ca537928SJennifer Lee                 for (auto &objpath : resp)
86*ca537928SJennifer Lee                 {
87*ca537928SJennifer Lee                     for (auto &interface : objpath.second)
88*ca537928SJennifer Lee                     {
89*ca537928SJennifer Lee                         // If interface is xyz.openbmc_project.Software.Version,
90*ca537928SJennifer Lee                         // this is what we're looking for.
91*ca537928SJennifer Lee                         if (interface.first ==
92*ca537928SJennifer Lee                             "xyz.openbmc_project.Software.Version")
93*ca537928SJennifer Lee                         {
94*ca537928SJennifer Lee                             // Cut out everyting until last "/", ...
95*ca537928SJennifer Lee                             const std::string &iface_id = objpath.first;
96*ca537928SJennifer Lee                             for (auto &property : interface.second)
97*ca537928SJennifer Lee                             {
98*ca537928SJennifer Lee                                 if (property.first == "Version")
99*ca537928SJennifer Lee                                 {
100*ca537928SJennifer Lee                                     const std::string *value =
101*ca537928SJennifer Lee                                         mapbox::getPtr<const std::string>(
102*ca537928SJennifer Lee                                             property.second);
103*ca537928SJennifer Lee                                     if (value == nullptr)
104*ca537928SJennifer Lee                                     {
105*ca537928SJennifer Lee                                         continue;
106*ca537928SJennifer Lee                                     }
107*ca537928SJennifer Lee                                     asyncResp->res
108*ca537928SJennifer Lee                                         .jsonValue["FirmwareVersion"] = *value;
109*ca537928SJennifer Lee                                 }
110*ca537928SJennifer Lee                             }
111*ca537928SJennifer Lee                         }
112*ca537928SJennifer Lee                     }
113*ca537928SJennifer Lee                 }
114*ca537928SJennifer Lee             },
115*ca537928SJennifer Lee             "xyz.openbmc_project.Software.BMC.Updater",
116*ca537928SJennifer Lee             "/xyz/openbmc_project/software",
117*ca537928SJennifer Lee             "org.freedesktop.DBus.ObjectManager", "GetManagedObjects");
1189c310685SBorawski.Lukasz     }
1199c310685SBorawski.Lukasz 
1201abe55efSEd Tanous     std::string getDateTime() const
1211abe55efSEd Tanous     {
1229c310685SBorawski.Lukasz         std::array<char, 128> dateTime;
1239c310685SBorawski.Lukasz         std::string redfishDateTime("0000-00-00T00:00:00Z00:00");
1249c310685SBorawski.Lukasz         std::time_t time = std::time(nullptr);
1259c310685SBorawski.Lukasz 
1269c310685SBorawski.Lukasz         if (std::strftime(dateTime.begin(), dateTime.size(), "%FT%T%z",
1271abe55efSEd Tanous                           std::localtime(&time)))
1281abe55efSEd Tanous         {
1299c310685SBorawski.Lukasz             // insert the colon required by the ISO 8601 standard
1309c310685SBorawski.Lukasz             redfishDateTime = std::string(dateTime.data());
1319c310685SBorawski.Lukasz             redfishDateTime.insert(redfishDateTime.end() - 2, ':');
1329c310685SBorawski.Lukasz         }
1339c310685SBorawski.Lukasz 
1349c310685SBorawski.Lukasz         return redfishDateTime;
1359c310685SBorawski.Lukasz     }
1369c310685SBorawski.Lukasz };
1379c310685SBorawski.Lukasz 
1381abe55efSEd Tanous class ManagerCollection : public Node
1391abe55efSEd Tanous {
1409c310685SBorawski.Lukasz   public:
1411abe55efSEd Tanous     ManagerCollection(CrowApp &app) : Node(app, "/redfish/v1/Managers/")
1421abe55efSEd Tanous     {
1439c310685SBorawski.Lukasz         Node::json["@odata.id"] = "/redfish/v1/Managers";
1449c310685SBorawski.Lukasz         Node::json["@odata.type"] = "#ManagerCollection.ManagerCollection";
1459c310685SBorawski.Lukasz         Node::json["@odata.context"] =
1469c310685SBorawski.Lukasz             "/redfish/v1/$metadata#ManagerCollection.ManagerCollection";
1479c310685SBorawski.Lukasz         Node::json["Name"] = "Manager Collection";
1489c310685SBorawski.Lukasz         Node::json["Members@odata.count"] = 1;
1491abe55efSEd Tanous         Node::json["Members"] = {
1501abe55efSEd Tanous             {{"@odata.id", "/redfish/v1/Managers/openbmc"}}};
1513ebd75f7SEd Tanous 
152a434f2bdSEd Tanous         entityPrivileges = {
153a434f2bdSEd Tanous             {boost::beast::http::verb::get, {{"Login"}}},
154e0d918bcSEd Tanous             {boost::beast::http::verb::head, {{"Login"}}},
155e0d918bcSEd Tanous             {boost::beast::http::verb::patch, {{"ConfigureManager"}}},
156e0d918bcSEd Tanous             {boost::beast::http::verb::put, {{"ConfigureManager"}}},
157e0d918bcSEd Tanous             {boost::beast::http::verb::delete_, {{"ConfigureManager"}}},
158e0d918bcSEd Tanous             {boost::beast::http::verb::post, {{"ConfigureManager"}}}};
1599c310685SBorawski.Lukasz     }
1609c310685SBorawski.Lukasz 
1619c310685SBorawski.Lukasz   private:
16255c7b7a2SEd Tanous     void doGet(crow::Response &res, const crow::Request &req,
1631abe55efSEd Tanous                const std::vector<std::string> &params) override
1641abe55efSEd Tanous     {
1651abe55efSEd Tanous         // Collections don't include the static data added by SubRoute because
1661abe55efSEd Tanous         // it has a duplicate entry for members
16755c7b7a2SEd Tanous         res.jsonValue["@odata.id"] = "/redfish/v1/Managers";
16855c7b7a2SEd Tanous         res.jsonValue["@odata.type"] = "#ManagerCollection.ManagerCollection";
16955c7b7a2SEd Tanous         res.jsonValue["@odata.context"] =
17055c7b7a2SEd Tanous             "/redfish/v1/$metadata#ManagerCollection.ManagerCollection";
17155c7b7a2SEd Tanous         res.jsonValue["Name"] = "Manager Collection";
17255c7b7a2SEd Tanous         res.jsonValue["Members@odata.count"] = 1;
17355c7b7a2SEd Tanous         res.jsonValue["Members"] = {
17455c7b7a2SEd Tanous             {{"@odata.id", "/redfish/v1/Managers/openbmc"}}};
1759c310685SBorawski.Lukasz         res.end();
1769c310685SBorawski.Lukasz     }
1779c310685SBorawski.Lukasz };
1789c310685SBorawski.Lukasz 
1799c310685SBorawski.Lukasz } // namespace redfish
180