xref: /openbmc/bmcweb/http/routing/baserule.hpp (revision 1b8b02a4)
1 #pragma once
2 
3 #include "async_resp.hpp"
4 #include "http_request.hpp"
5 #include "privileges.hpp"
6 #include "verb.hpp"
7 
8 #include <boost/beast/ssl/ssl_stream.hpp>
9 
10 #include <memory>
11 #include <string>
12 
13 namespace crow
14 {
15 class BaseRule
16 {
17   public:
18     explicit BaseRule(const std::string& thisRule) : rule(thisRule) {}
19 
20     virtual ~BaseRule() = default;
21 
22     BaseRule(const BaseRule&) = delete;
23     BaseRule(BaseRule&&) = delete;
24     BaseRule& operator=(const BaseRule&) = delete;
25     BaseRule& operator=(const BaseRule&&) = delete;
26 
27     virtual void validate() = 0;
28     std::unique_ptr<BaseRule> upgrade()
29     {
30         if (ruleToUpgrade)
31         {
32             return std::move(ruleToUpgrade);
33         }
34         return {};
35     }
36 
37     virtual void handle(const Request& /*req*/,
38                         const std::shared_ptr<bmcweb::AsyncResp>&,
39                         const std::vector<std::string>&) = 0;
40 #ifndef BMCWEB_ENABLE_SSL
41     virtual void
42         handleUpgrade(const Request& /*req*/,
43                       const std::shared_ptr<bmcweb::AsyncResp>& asyncResp,
44                       boost::asio::ip::tcp::socket&& /*adaptor*/)
45     {
46         asyncResp->res.result(boost::beast::http::status::not_found);
47     }
48 #else
49     virtual void handleUpgrade(
50         const Request& /*req*/,
51         const std::shared_ptr<bmcweb::AsyncResp>& asyncResp,
52         boost::beast::ssl_stream<boost::asio::ip::tcp::socket>&& /*adaptor*/)
53     {
54         asyncResp->res.result(boost::beast::http::status::not_found);
55     }
56 #endif
57 
58     size_t getMethods() const
59     {
60         return methodsBitfield;
61     }
62 
63     bool checkPrivileges(const redfish::Privileges& userPrivileges)
64     {
65         // If there are no privileges assigned, assume no privileges
66         // required
67         if (privilegesSet.empty())
68         {
69             return true;
70         }
71 
72         for (const redfish::Privileges& requiredPrivileges : privilegesSet)
73         {
74             if (userPrivileges.isSupersetOf(requiredPrivileges))
75             {
76                 return true;
77             }
78         }
79         return false;
80     }
81 
82     size_t methodsBitfield{1 << static_cast<size_t>(HttpVerb::Get)};
83     static_assert(std::numeric_limits<decltype(methodsBitfield)>::digits >
84                       methodNotAllowedIndex,
85                   "Not enough bits to store bitfield");
86 
87     std::vector<redfish::Privileges> privilegesSet;
88 
89     std::string rule;
90 
91     std::unique_ptr<BaseRule> ruleToUpgrade;
92 
93     friend class Router;
94     template <typename T>
95     friend struct RuleParameterTraits;
96 };
97 
98 } // namespace crow
99