1 /* 2 // Copyright (c) 2019 Intel Corporation 3 // 4 // Licensed under the Apache License, Version 2.0 (the "License"); 5 // you may not use this file except in compliance with the License. 6 // You may obtain a copy of the License at 7 // 8 // http://www.apache.org/licenses/LICENSE-2.0 9 // 10 // Unless required by applicable law or agreed to in writing, software 11 // distributed under the License is distributed on an "AS IS" BASIS, 12 // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 // See the License for the specific language governing permissions and 14 // limitations under the License. 15 */ 16 #pragma once 17 18 #include "node.hpp" 19 #include "registries.hpp" 20 #include "registries/base_message_registry.hpp" 21 #include "registries/openbmc_message_registry.hpp" 22 #include "registries/task_event_message_registry.hpp" 23 24 namespace redfish 25 { 26 27 class MessageRegistryFileCollection : public Node 28 { 29 public: 30 template <typename CrowApp> 31 MessageRegistryFileCollection(CrowApp& app) : 32 Node(app, "/redfish/v1/Registries/") 33 { 34 entityPrivileges = { 35 {boost::beast::http::verb::get, {{"Login"}}}, 36 {boost::beast::http::verb::head, {{"Login"}}}, 37 {boost::beast::http::verb::patch, {{"ConfigureManager"}}}, 38 {boost::beast::http::verb::put, {{"ConfigureManager"}}}, 39 {boost::beast::http::verb::delete_, {{"ConfigureManager"}}}, 40 {boost::beast::http::verb::post, {{"ConfigureManager"}}}}; 41 } 42 43 private: 44 /** 45 * Functions triggers appropriate requests on DBus 46 */ 47 void doGet(crow::Response& res, const crow::Request& req, 48 const std::vector<std::string>& params) override 49 { 50 // Collections don't include the static data added by SubRoute because 51 // it has a duplicate entry for members 52 53 res.jsonValue = { 54 {"@odata.type", 55 "#MessageRegistryFileCollection.MessageRegistryFileCollection"}, 56 {"@odata.id", "/redfish/v1/Registries"}, 57 {"Name", "MessageRegistryFile Collection"}, 58 {"Description", "Collection of MessageRegistryFiles"}, 59 {"Members@odata.count", 3}, 60 {"Members", 61 {{{"@odata.id", "/redfish/v1/Registries/Base"}}, 62 {{"@odata.id", "/redfish/v1/Registries/TaskEvent"}}, 63 {{"@odata.id", "/redfish/v1/Registries/OpenBMC"}}}}}; 64 65 res.end(); 66 } 67 }; 68 69 class MessageRegistryFile : public Node 70 { 71 public: 72 template <typename CrowApp> 73 MessageRegistryFile(CrowApp& app) : 74 Node(app, "/redfish/v1/Registries/<str>/", std::string()) 75 { 76 entityPrivileges = { 77 {boost::beast::http::verb::get, {{"Login"}}}, 78 {boost::beast::http::verb::head, {{"Login"}}}, 79 {boost::beast::http::verb::patch, {{"ConfigureManager"}}}, 80 {boost::beast::http::verb::put, {{"ConfigureManager"}}}, 81 {boost::beast::http::verb::delete_, {{"ConfigureManager"}}}, 82 {boost::beast::http::verb::post, {{"ConfigureManager"}}}}; 83 } 84 85 private: 86 void doGet(crow::Response& res, const crow::Request& req, 87 const std::vector<std::string>& params) override 88 { 89 if (params.size() != 1) 90 { 91 messages::internalError(res); 92 res.end(); 93 return; 94 } 95 96 const std::string& registry = params[0]; 97 const message_registries::Header* header; 98 std::string dmtf = "DMTF "; 99 const char* url = nullptr; 100 101 if (registry == "Base") 102 { 103 header = &message_registries::base::header; 104 url = message_registries::base::url; 105 } 106 else if (registry == "TaskEvent") 107 { 108 header = &message_registries::task_event::header; 109 url = message_registries::task_event::url; 110 } 111 else if (registry == "OpenBMC") 112 { 113 header = &message_registries::openbmc::header; 114 dmtf.clear(); 115 } 116 else 117 { 118 messages::resourceNotFound( 119 res, "#MessageRegistryFile.v1_1_0.MessageRegistryFile", 120 registry); 121 res.end(); 122 return; 123 } 124 125 res.jsonValue = { 126 {"@odata.id", "/redfish/v1/Registries/" + registry}, 127 {"@odata.type", "#MessageRegistryFile.v1_1_0.MessageRegistryFile"}, 128 {"Name", registry + " Message Registry File"}, 129 {"Description", 130 dmtf + registry + " Message Registry File Location"}, 131 {"Id", header->registryPrefix}, 132 {"Registry", header->id}, 133 {"Languages", {"en"}}, 134 {"Languages@odata.count", 1}, 135 {"Location", 136 {{{"Language", "en"}, 137 {"Uri", 138 "/redfish/v1/Registries/" + registry + "/" + registry}}}}, 139 {"Location@odata.count", 1}}; 140 141 if (url != nullptr) 142 { 143 res.jsonValue["Location"][0]["PublicationUri"] = url; 144 } 145 146 res.end(); 147 } 148 }; 149 150 class MessageRegistry : public Node 151 { 152 public: 153 template <typename CrowApp> 154 MessageRegistry(CrowApp& app) : 155 Node(app, "/redfish/v1/Registries/<str>/<str>/", std::string(), 156 std::string()) 157 { 158 entityPrivileges = { 159 {boost::beast::http::verb::get, {{"Login"}}}, 160 {boost::beast::http::verb::head, {{"Login"}}}, 161 {boost::beast::http::verb::patch, {{"ConfigureManager"}}}, 162 {boost::beast::http::verb::put, {{"ConfigureManager"}}}, 163 {boost::beast::http::verb::delete_, {{"ConfigureManager"}}}, 164 {boost::beast::http::verb::post, {{"ConfigureManager"}}}}; 165 } 166 167 private: 168 void doGet(crow::Response& res, const crow::Request& req, 169 const std::vector<std::string>& params) override 170 { 171 if (params.size() != 2) 172 { 173 messages::internalError(res); 174 res.end(); 175 return; 176 } 177 178 const std::string& registry = params[0]; 179 const std::string& registry1 = params[1]; 180 181 const message_registries::Header* header; 182 std::vector<const message_registries::MessageEntry*> registryEntries; 183 if (registry == "Base") 184 { 185 header = &message_registries::base::header; 186 for (const message_registries::MessageEntry& entry : 187 message_registries::base::registry) 188 { 189 registryEntries.emplace_back(&entry); 190 } 191 } 192 else if (registry == "TaskEvent") 193 { 194 header = &message_registries::task_event::header; 195 for (const message_registries::MessageEntry& entry : 196 message_registries::task_event::registry) 197 { 198 registryEntries.emplace_back(&entry); 199 } 200 } 201 else if (registry == "OpenBMC") 202 { 203 header = &message_registries::openbmc::header; 204 for (const message_registries::MessageEntry& entry : 205 message_registries::openbmc::registry) 206 { 207 registryEntries.emplace_back(&entry); 208 } 209 } 210 else 211 { 212 messages::resourceNotFound( 213 res, "#MessageRegistryFile.v1_1_0.MessageRegistryFile", 214 registry); 215 res.end(); 216 return; 217 } 218 219 if (registry != registry1) 220 { 221 messages::resourceNotFound(res, header->type, registry1); 222 res.end(); 223 return; 224 } 225 226 res.jsonValue = {{"@Redfish.Copyright", header->copyright}, 227 {"@odata.type", header->type}, 228 {"Id", header->id}, 229 {"Name", header->name}, 230 {"Language", header->language}, 231 {"Description", header->description}, 232 {"RegistryPrefix", header->registryPrefix}, 233 {"RegistryVersion", header->registryVersion}, 234 {"OwningEntity", header->owningEntity}}; 235 236 nlohmann::json& messageObj = res.jsonValue["Messages"]; 237 238 // Go through the Message Registry and populate each Message 239 for (const message_registries::MessageEntry* message : registryEntries) 240 { 241 nlohmann::json& obj = messageObj[message->first]; 242 obj = {{"Description", message->second.description}, 243 {"Message", message->second.message}, 244 {"Severity", message->second.severity}, 245 {"MessageSeverity", message->second.messageSeverity}, 246 {"NumberOfArgs", message->second.numberOfArgs}, 247 {"Resolution", message->second.resolution}}; 248 if (message->second.numberOfArgs > 0) 249 { 250 nlohmann::json& messageParamArray = obj["ParamTypes"]; 251 for (const char* str : message->second.paramTypes) 252 { 253 if (str == nullptr) 254 { 255 break; 256 } 257 messageParamArray.push_back(str); 258 } 259 } 260 } 261 res.end(); 262 } 263 }; 264 265 } // namespace redfish 266