From 95b417bb36bdaa3af393a501f21492b39177d9a6 Mon Sep 17 00:00:00 2001 From: Lion Kortlepel Date: Wed, 2 Mar 2022 11:43:48 +0100 Subject: [PATCH] Add MP.JsonSerialize --- include/LuaAPI.h | 1 + src/LuaAPI.cpp | 76 ++++++++++++++++++++++++++++++++++++++++++++++ src/TLuaEngine.cpp | 3 ++ 3 files changed, 80 insertions(+) diff --git a/include/LuaAPI.h b/include/LuaAPI.h index 0cd0e1f..f7530d0 100644 --- a/include/LuaAPI.h +++ b/include/LuaAPI.h @@ -22,6 +22,7 @@ namespace MP { bool IsPlayerConnected(int ID); void Sleep(size_t Ms); void PrintRaw(sol::variadic_args); + std::string JsonSerialize(sol::table object); } namespace FS { std::pair CreateDirectory(const std::string& Path); diff --git a/src/LuaAPI.cpp b/src/LuaAPI.cpp index 14cd8f6..5e60a16 100644 --- a/src/LuaAPI.cpp +++ b/src/LuaAPI.cpp @@ -3,6 +3,8 @@ #include "Common.h" #include "TLuaEngine.h" +#include + #define SOL_ALL_SAFETIES_ON 1 #include @@ -351,3 +353,77 @@ std::string LuaAPI::FS::ConcatPaths(sol::variadic_args Args) { auto Result = Path.lexically_normal().string(); return Result; } + +static void JsonSerializeRecursive(nlohmann::json& json, sol::object left, sol::object right) { + std::string key; + bool is_array = false; + switch (left.get_type()) { + case sol::type::lua_nil: + case sol::type::none: + case sol::type::poly: + case sol::type::boolean: + case sol::type::lightuserdata: + case sol::type::userdata: + case sol::type::thread: + case sol::type::function: + case sol::type::table: + beammp_lua_error("JsonSerialize: left side of table field is unexpected type"); + return; + case sol::type::string: + key = left.as(); + break; + case sol::type::number: + is_array = true; + // TODO: deal with this + break; + } + nlohmann::json value; + switch (right.get_type()) { + case sol::type::lua_nil: + case sol::type::none: + return; + case sol::type::poly: + beammp_lua_warn("unsure what to do with poly type in JsonSerialize, ignoring"); + break; + case sol::type::boolean: + value = right.as(); + break; + case sol::type::lightuserdata: + beammp_lua_warn("unsure what to do with lightuserdata in JsonSerialize, ignoring"); + break; + case sol::type::userdata: + beammp_lua_warn("unsure what to do with userdata in JsonSerialize, ignoring"); + break; + case sol::type::thread: + beammp_lua_warn("unsure what to do with thread in JsonSerialize, ignoring"); + break; + case sol::type::string: + value = right.as(); + break; + case sol::type::number: + value = right.as(); + break; + case sol::type::function: + beammp_lua_warn("unsure what to do with function in JsonSerialize, ignoring"); + break; + case sol::type::table: + for (const auto& pair : right.as()) { + JsonSerializeRecursive(value, pair.first, pair.second); + } + break; + } + if (is_array) { + json.push_back(value); + } else { + json[key] = value; + } +} + +std::string LuaAPI::MP::JsonSerialize(sol::table object) { + nlohmann::json json; + // table + for (const auto& entry : object) { + JsonSerializeRecursive(json, entry.first, entry.second); + } + return json.dump(); +} diff --git a/src/TLuaEngine.cpp b/src/TLuaEngine.cpp index db25919..3f1ec58 100644 --- a/src/TLuaEngine.cpp +++ b/src/TLuaEngine.cpp @@ -556,10 +556,13 @@ TLuaEngine::StateThreadData::StateThreadData(const std::string& Name, std::atomi mEngine->CancelEventTimers(EventName, mStateId); }); MPTable.set_function("Set", &LuaAPI::MP::Set); + MPTable.set_function("JsonSerialize", &LuaAPI::MP::JsonSerialize); + auto HttpTable = StateView.create_named_table("Http"); HttpTable.set_function("CreateConnection", [this](const std::string& host, uint16_t port) { return Lua_HttpCreateConnection(host, port); }); + MPTable.create_named("Settings", "Debug", 0,