#ifndef __SICCCPERSISTER_H_ #define __SICCCPERSISTER_H_ #include "Routerin.H" #include "sicccobject.H" #include #include #include #include #include #include class SicccPersister { public: static json_t * load_json(const std::string &s) { assert(!s.empty()); std::cout << "[DEBUG] joad_json: " << s << std::endl; json_t *root = nullptr; json_error_t error; root = json_load_file(s.c_str(), JSON_DECODE_ANY, &error); if (!root) { /* std::cerr << "[read_json] " << error << std::endl; */ return nullptr; } return root; } static std::string get_string_from_json(const json_t *j) { assert(j); assert(json_is_string(j)); const char *tmp = json_string_value(j); assert(tmp); return std::string(tmp); } static json_t *get_json_from_string(const std::string &s) { json_t* ret = json_string(s.c_str()); assert(ret); return ret; } static unsigned int get_integer_from_json(const json_t *j) { assert(j); assert(json_is_integer(j)); return json_integer_value(j); } static json_t *get_json_from_integer(const unsigned int value) { assert(value); json_t* ret = json_integer(value); assert(ret); return ret; } static std::chrono::time_point get_time_from_json(const json_t *j) { assert(j); auto tmp = get_string_from_json(j); time_t t = stol(tmp); return std::chrono::system_clock::from_time_t(t); } static std::string time_to_string(const std::chrono::time_point& t) { time_t time = std::chrono::system_clock::to_time_t(t); std::string ret = std::to_string(time); return ret; } /** TODO * implement bool operator to take advantages of the use of assert */ static json_t *get_json_from_sicccobject(const Sicccobject& so) { json_t *root = json_object(); json_object_set_new(root, "filename", get_json_from_string(so.get_filename())); json_object_set_new(root, "filetype", get_json_from_string(so.get_filetype())); json_object_set_new(root, "path", get_json_from_string(so.get_filepath())); json_object_set_new(root, "size", get_json_from_integer(so.get_size())); std::string tmp = time_to_string(so.get_uploadtime()); json_object_set_new(root, "upload_time", get_json_from_string(tmp)); assert(root); return root; } static std::string get_json_string_representation(const json_t *j) { assert(j); assert(json_is_object(j)); const char *tmp = json_dumps(j, JSON_INDENT(4)); assert(tmp); std::string ret(tmp); free((void*) tmp); return ret; } static std::vector read_sicccdir(const Routerin &merouter = *Routerin::get_instance()) { DIR *dir = nullptr; struct dirent *entry = nullptr; std::vector v; std::string json_path = merouter.get_json_path(); json_error_t *error = nullptr; std::cout << "[DEBUG] in reading sicccdir" << std::endl; if ((dir = opendir(json_path.c_str())) == NULL) { std::cerr << "Error could not open directory" << std::endl; return v; // should throw exception instea1d } while ((entry = readdir(dir)) != NULL) { if (std::strstr(entry->d_name, ".json") == NULL) continue; std::cout << entry->d_name << std::endl; json_t *tmp = json_load_file((json_path + std::string(entry->d_name)).c_str(), JSON_DECODE_ANY, error); assert(tmp); Sicccobject so(tmp); v.push_back(so); } return v; } public: SicccPersister(const Routerin & merouter = *Routerin::get_instance()) : merouter(merouter) { root = json_object(); json_file_name = "foo.json"; // not the best default }; SicccPersister(const Sicccobject& so,const Routerin &merouter = * Routerin::get_instance()): merouter(merouter) { root = get_json_from_sicccobject(so); json_file_name = so.get_filename(); } SicccPersister(json_t *j, const Routerin & merouter =* Routerin::get_instance()): merouter(merouter) { root = json_object(); json_object_update(root, j); } ~SicccPersister() { if (root) json_decref(root); } int write_sicccfile(const Sicccobject&); int write_sicccfile(); Sicccobject read_json(const std::string&); Sicccobject read_json() { return read_json(json_file_name); } friend std::ostream& operator << (std::ostream& out, const SicccPersister &p) { out << get_json_string_representation(p.root); return out; } friend std::ostream& operator << (std::ostream& out, const json_t *j) { assert(j); out << get_json_string_representation(j); return out; } private: const Routerin & merouter; std::string json_file_name; json_t *root; std::string inline beautify_filename() { std::string s; if (json_file_name.empty()) return s; size_t pos = json_file_name.find_last_of("."); s = json_file_name.substr(0, pos + 1); s.append("json"); return s; } }; #endif /* __SICCCPERSISTER_H_ */