1 #pragma once
2 
3 #include "external_storer_interface.hpp"
4 #include "nlohmann/json.hpp"
5 #include "notifier_dbus_handler.hpp"
6 
7 #include <boost/uuid/uuid_generators.hpp>
8 
9 #include <filesystem>
10 #include <queue>
11 #include <string>
12 
13 namespace bios_bmc_smm_error_logger
14 {
15 namespace rde
16 {
17 
18 /**
19  * @brief Simple Base class for writing JSON data to files.
20  *
21  * This class allows us to unit test the ExternalStorerFileInterface
22  * functionality.
23  */
24 class FileHandlerInterface
25 {
26   public:
27     virtual ~FileHandlerInterface() = default;
28 
29     /**
30      * @brief Create a folder at the provided path.
31      *
32      * @param[in] folderPath - folder path.
33      * @return true if successful.
34      */
35     virtual bool createFolder(const std::string& folderPath) const = 0;
36 
37     /**
38      * @brief Create an index.json and write the JSON content to it.
39      *
40      * If the file already exists, this will overwrite it.
41      *
42      * @param[in] folderPath - path of the file without including the file name.
43      * @param[in] jsonPdr - PDR in nlohmann::json format.
44      * @return true if successful.
45      */
46     virtual bool createFile(const std::string& folderPath,
47                             const nlohmann::json& jsonPdr) const = 0;
48 
49     /**
50      * @brief Call remove_all on the filePath
51      *
52      * @param[in] filePath - path of the file/folder to remove
53      * @return true if successful.
54      */
55     virtual bool removeAll(const std::string& filePath) const = 0;
56 };
57 
58 /**
59  * @brief Class for handling folder and file creation for ExternalStorer.
60  */
61 class ExternalStorerFileWriter : public FileHandlerInterface
62 {
63   public:
64     bool createFolder(const std::string& folderPath) const override;
65     bool createFile(const std::string& folderPath,
66                     const nlohmann::json& jsonPdr) const override;
67     bool removeAll(const std::string& filePath) const override;
68 };
69 
70 /**
71  * @brief Categories for different redfish JSON strings.
72  */
73 enum class JsonPdrType
74 {
75     logEntry,
76     logService,
77     other
78 };
79 
80 /**
81  * @brief Class for handling ExternalStorer file operations.
82  */
83 class ExternalStorerFileInterface : public ExternalStorerInterface
84 {
85   public:
86     /**
87      * @brief Constructor for the ExternalStorerFileInterface.
88      *
89      * @param[in] conn - sdbusplus asio connection.
90      * @param[in] rootPath - root path for creating redfish folders.
91      * Eg: "/run/bmcweb"
92      * @param[in] fileHandler - an ExternalStorerFileWriter object. This class
93      * will take the ownership of this object.
94      * @param[in] numSavedLogEntries - first N number of log entries to be saved
95      * in the queue (default shall be 20)
96      * @param[in] numLogEntries - number of non-saved log entries in the queue
97      * (default shall be 1000 - 20 = 980)
98      */
99     ExternalStorerFileInterface(
100         const std::shared_ptr<sdbusplus::asio::connection>& conn,
101         std::string_view rootPath,
102         std::unique_ptr<FileHandlerInterface> fileHandler,
103         uint32_t numSavedLogEntries = 20, uint32_t numLogEntries = 980);
104 
105     bool publishJson(std::string_view jsonStr) override;
106 
107   private:
108     std::string rootPath;
109     std::unique_ptr<FileHandlerInterface> fileHandler;
110     std::string logServiceId;
111     std::unique_ptr<CperFileNotifierHandler> cperNotifier;
112     boost::uuids::random_generator randomGen;
113     std::queue<std::string> logEntrySavedQueue;
114     std::queue<std::string> logEntryQueue;
115     // Default should be 20
116     const uint32_t maxNumSavedLogEntries;
117     // Default should be 1000 - maxNumSavedLogEntries(20) = 980
118     const uint32_t maxNumLogEntries;
119 
120     /**
121      * @brief Get the type of the received PDR.
122      *
123      * @param[in] jsonSchema - PDR in nlohmann::json format.
124      * @return JsonPdrType of the PDR.
125      */
126     JsonPdrType getSchemaType(const nlohmann::json& jsonSchema) const;
127 
128     /**
129      * @brief Process a LogEntry type PDR.
130      *
131      * @param[in] logEntry - PDR in nlohmann::json format.
132      * @return true if successful.
133      */
134     bool processLogEntry(nlohmann::json& logEntry);
135 
136     /**
137      * @brief Process a LogService type PDR.
138      *
139      * @param[in] logService - PDR in nlohmann::json format.
140      * @return true if successful.
141      */
142     bool processLogService(const nlohmann::json& logService);
143 
144     /**
145      * @brief Process PDRs that doesn't have a specific category.
146      *
147      * @param[in] jsonPdr - PDR in nlohmann::json format.
148      * @return true if successful.
149      */
150     bool processOtherTypes(const nlohmann::json& jsonPdr) const;
151 
152     /**
153      * @brief Create the needed folders and the index.json.
154      *
155      * @param subPath - path within the root folder.
156      * @param jsonPdr - PDR in nlohmann::json format.
157      * @return true if successful.
158      */
159     bool createFile(const std::string& subPath,
160                     const nlohmann::json& jsonPdr) const;
161 };
162 
163 } // namespace rde
164 } // namespace bios_bmc_smm_error_logger
165