diff options
Diffstat (limited to 'modules/rpc')
| -rw-r--r-- | modules/rpc/jsonrpc.cpp | 104 | ||||
| -rw-r--r-- | modules/rpc/rpc_main.cpp | 72 |
2 files changed, 90 insertions, 86 deletions
diff --git a/modules/rpc/jsonrpc.cpp b/modules/rpc/jsonrpc.cpp index b7c1f4042..ad46bcb13 100644 --- a/modules/rpc/jsonrpc.cpp +++ b/modules/rpc/jsonrpc.cpp @@ -59,46 +59,24 @@ private: yyjson_mut_doc_free(doc); } - static void SerializeMap(yyjson_mut_doc *doc, yyjson_mut_val *root, const char *key, const RPC::Map &map) + static yyjson_mut_val *SerializeElement(yyjson_mut_doc *doc, const RPC::Value &value); + + static void SerializeArray(yyjson_mut_doc *doc, yyjson_mut_val *value, const RPC::Array &array) { - auto *result = yyjson_mut_obj(doc); - for (const auto &reply : map.GetReplies()) - { - // Captured structured bindings are a C++20 extension. - const auto &k = reply.first; - std::visit(overloaded - { - [&doc, &result, &k](const RPC::Map &m) - { - SerializeMap(doc, result, k.c_str(), m); - }, - [&doc, &result, &k](const Anope::string &s) - { - yyjson_mut_obj_add_strn(doc, result, k.c_str(), s.c_str(), s.length()); - }, - [&doc, &result, &k](std::nullptr_t) - { - yyjson_mut_obj_add_null(doc, result, k.c_str()); - }, - [&doc, &result, &k](bool b) - { - yyjson_mut_obj_add_bool(doc, result, k.c_str(), b); - }, - [&doc, &result, &k](double d) - { - yyjson_mut_obj_add_real(doc, result, k.c_str(), d); - }, - [&doc, &result, &k](int64_t i) - { - yyjson_mut_obj_add_int(doc, result, k.c_str(), i); - }, - [&doc, &result, &k](uint64_t u) - { - yyjson_mut_obj_add_uint(doc, result, k.c_str(), u); - }, - }, reply.second); + for (const auto &elem : array.GetReplies()) + { + auto *obj = SerializeElement(doc, elem); + yyjson_mut_arr_add_val(value, obj); + } + } + + static void SerializeMap(yyjson_mut_doc *doc, yyjson_mut_val *value, const RPC::Map &map) + { + for (const auto &[k, v] : map.GetReplies()) + { + auto *obj = SerializeElement(doc, v); + yyjson_mut_obj_add_val(doc, value, k.c_str(), obj); } - yyjson_mut_obj_add_val(doc, root, key, result); } public: @@ -194,7 +172,11 @@ public: yyjson_mut_obj_add_strn(doc, root, "id", request.id.c_str(), request.id.length()); if (!request.GetReplies().empty()) - SerializeMap(doc, root, "result", request); + { + auto *result = yyjson_mut_obj(doc); + SerializeMap(doc, result, request); + yyjson_mut_obj_add_val(doc, root, "result", result); + } yyjson_mut_obj_add_str(doc, root, "jsonrpc", "2.0"); @@ -208,6 +190,50 @@ public: } }; +yyjson_mut_val *MyJSONRPCServiceInterface::SerializeElement(yyjson_mut_doc *doc, const RPC::Value &value) +{ + yyjson_mut_val *elem; + std::visit(overloaded + { + [&doc, &elem](const RPC::Array &a) + { + elem = yyjson_mut_arr(doc); + SerializeArray(doc, elem, a); + }, + [&doc, &elem](const RPC::Map &m) + { + elem = yyjson_mut_obj(doc); + SerializeMap(doc, elem, m); + }, + [&doc, &elem](const Anope::string &s) + { + elem = yyjson_mut_strn(doc, s.c_str(), s.length()); + }, + [&doc, &elem](std::nullptr_t) + { + elem = yyjson_mut_null(doc); + }, + [&doc, &elem](bool b) + { + elem = yyjson_mut_bool(doc, b); + }, + [&doc, &elem](double d) + { + elem = yyjson_mut_real(doc, d); + }, + [&doc, &elem](int64_t i) + { + elem = yyjson_mut_int(doc, i); + }, + [&doc, &elem](uint64_t u) + { + elem = yyjson_mut_uint(doc, u); + }, + }, value.Get()); + return elem; +} + + class ModuleJSONRPC final : public Module { diff --git a/modules/rpc/rpc_main.cpp b/modules/rpc/rpc_main.cpp index 7be09be22..c1e53e8dd 100644 --- a/modules/rpc/rpc_main.cpp +++ b/modules/rpc/rpc_main.cpp @@ -152,19 +152,16 @@ public: bool Run(RPC::ServiceInterface *iface, HTTPClient *client, RPC::Request &request) override { - request.ReplyInt("uptime", Anope::CurTime - Anope::StartTime); + request.Reply("uptime", Anope::CurTime - Anope::StartTime); request.Reply("uplinkname", Me->GetLinks().front()->GetName()); { - Anope::string buf; + auto &uplinkcapab = request.ReplyArray("uplinkcapab"); for (const auto &capab : Servers::Capab) - buf += " " + capab; - if (!buf.empty()) - buf.erase(buf.begin()); - request.Reply("uplinkcapab", buf); + uplinkcapab.Reply(capab); } - request.ReplyUInt("usercount", UserListByNick.size()); - request.ReplyUInt("maxusercount", MaxUserCount); - request.ReplyUInt("channelcount", ChannelList.size()); + request.Reply("usercount", UserListByNick.size()); + request.Reply("maxusercount", MaxUserCount); + request.Reply("channelcount", ChannelList.size()); return true; } }; @@ -192,35 +189,24 @@ public: if (c) { - auto &bans = request.ReplyMap("bans"); - bans.ReplyUInt("count", c->HasMode("BAN")); - int count = 0; + request.Reply("bancount", c->HasMode("BAN")); + auto &bans = request.ReplyArray("bans"); for (auto &ban : c->GetModeList("BAN")) - bans.Reply(Anope::ToString(++count), ban); + bans.Reply(ban); - auto &excepts = request.ReplyMap("excepts"); - excepts.ReplyUInt("count", c->HasMode("EXCEPT")); - count = 0; + request.Reply("exceptcount", c->HasMode("EXCEPT")); + auto &excepts = request.ReplyArray("excepts"); for (auto &except : c->GetModeList("EXCEPT")) - excepts.Reply(Anope::ToString(++count), except); + excepts.Reply(except); - auto &invites = request.ReplyMap("invites"); - invites.ReplyUInt("count", c->HasMode("INVITEOVERRIDE")); - count = 0; + request.Reply("invitecount", c->HasMode("INVITEOVERRIDE")); + auto &invites = request.ReplyArray("invites"); for (auto &invite : c->GetModeList("INVITEOVERRIDE")) - invites.Reply(Anope::ToString(++count), invite); + invites.Reply(invite); - Anope::string users; - for (Channel::ChanUserList::const_iterator it = c->users.begin(); it != c->users.end(); ++it) - { - ChanUserContainer *uc = it->second; - users += uc->status.BuildModePrefixList() + uc->user->nick + " "; - } - if (!users.empty()) - { - users.erase(users.length() - 1); - request.Reply("users", users); - } + auto &users = request.ReplyArray("users"); + for (const auto &[_, uc] : c->users) + users.Reply(uc->status.BuildModePrefixList() + uc->user->nick); if (!c->topic.empty()) request.Reply("topic", c->topic); @@ -228,8 +214,8 @@ public: if (!c->topic_setter.empty()) request.Reply("topicsetter", c->topic_setter); - request.ReplyInt("topictime", c->topic_time); - request.ReplyInt("topicts", c->topic_ts); + request.Reply("topictime", c->topic_time); + request.Reply("topicts", c->topic_ts); } return true; } @@ -266,8 +252,8 @@ public: if (!u->chost.empty()) request.Reply("chost", u->chost); request.Reply("ip", u->ip.addr()); - request.ReplyUInt("timestamp", u->timestamp); - request.ReplyUInt("signon", u->signon); + request.Reply("timestamp", u->timestamp); + request.Reply("signon", u->signon); if (u->IsIdentified()) { request.Reply("account", u->Account()->display); @@ -275,17 +261,9 @@ public: request.Reply("opertype", u->Account()->o->ot->GetName()); } - Anope::string channels; - for (User::ChanUserList::const_iterator it = u->chans.begin(); it != u->chans.end(); ++it) - { - ChanUserContainer *cc = it->second; - channels += cc->status.BuildModePrefixList() + cc->chan->name + " "; - } - if (!channels.empty()) - { - channels.erase(channels.length() - 1); - request.Reply("channels", channels); - } + auto &channels = request.ReplyArray("channels"); + for (const auto &[_, cc] : u->chans) + channels.Reply(cc->status.BuildModePrefixList() + cc->chan->name); } return true; } |
