summary refs log tree commit diff
path: root/src/Cache_p.h
diff options
context:
space:
mode:
authorNicolas Werner <nicolas.werner@hotmail.de>2023-10-30 14:56:10 +0100
committerNicolas Werner <nicolas.werner@hotmail.de>2023-10-31 13:04:39 +0100
commit99a3e8bcf2f9ed58589638fb6a9d4f2bdf3c6b91 (patch)
tree67eab63711e16c1a0794d94928755857586cb35f /src/Cache_p.h
parentSet version in msix (diff)
downloadnheko-99a3e8bcf2f9ed58589638fb6a9d4f2bdf3c6b91.tar.xz
Speed up compilation a bit
Diffstat (limited to 'src/Cache_p.h')
-rw-r--r--src/Cache_p.h221
1 files changed, 35 insertions, 186 deletions
diff --git a/src/Cache_p.h b/src/Cache_p.h
index e59796ed..d1316ae5 100644
--- a/src/Cache_p.h
+++ b/src/Cache_p.h
@@ -4,7 +4,6 @@
 
 #pragma once
 
-#include <limits>
 #include <optional>
 
 #include <QDateTime>
@@ -15,8 +14,8 @@
 #else
 #include <lmdb++.h>
 #endif
-#include <nlohmann/json.hpp>
 
+#include <mtx/events/collections.hpp>
 #include <mtx/responses/notifications.hpp>
 #include <mtx/responses/sync.hpp>
 #include <mtxclient/crypto/types.hpp>
@@ -24,7 +23,6 @@
 
 #include "CacheCryptoStructs.h"
 #include "CacheStructs.h"
-#include "Logging.h"
 
 namespace mtx::responses {
 struct Messages;
@@ -364,8 +362,6 @@ private:
                        mtx::events::collections::TimelineEvents e,
                        const std::string &room_id);
 
-    //! Remove a room from the cache.
-    // void removeLeftRoom(lmdb::txn &txn, const std::string &room_id);
     template<class T>
     void saveStateEvents(lmdb::txn &txn,
                          lmdb::dbi &statesdb,
@@ -373,11 +369,7 @@ private:
                          lmdb::dbi &membersdb,
                          lmdb::dbi &eventsDb,
                          const std::string &room_id,
-                         const std::vector<T> &events)
-    {
-        for (const auto &e : events)
-            saveStateEvent(txn, statesdb, stateskeydb, membersdb, eventsDb, room_id, e);
-    }
+                         const std::vector<T> &events);
 
     template<class T>
     void saveStateEvent(lmdb::txn &txn,
@@ -386,191 +378,18 @@ private:
                         lmdb::dbi &membersdb,
                         lmdb::dbi &eventsDb,
                         const std::string &room_id,
-                        const T &event)
-    {
-        using namespace mtx::events;
-        using namespace mtx::events::state;
-
-        if (auto e = std::get_if<StateEvent<Member>>(&event); e != nullptr) {
-            switch (e->content.membership) {
-            //
-            // We only keep users with invite or join membership.
-            //
-            case Membership::Invite:
-            case Membership::Join: {
-                auto display_name =
-                  e->content.display_name.empty() ? e->state_key : e->content.display_name;
-
-                std::string inviter = "";
-                if (e->content.membership == mtx::events::state::Membership::Invite) {
-                    inviter = e->sender;
-                }
-
-                // Lightweight representation of a member.
-                MemberInfo tmp{
-                  display_name,
-                  e->content.avatar_url,
-                  inviter,
-                  e->content.reason,
-                  e->content.is_direct,
-                };
-
-                membersdb.put(txn, e->state_key, nlohmann::json(tmp).dump());
-                break;
-            }
-            default: {
-                membersdb.del(txn, e->state_key, "");
-                break;
-            }
-            }
-        } else if (auto encr = std::get_if<StateEvent<Encryption>>(&event)) {
-            if (!encr->state_key.empty())
-                return;
-
-            setEncryptedRoom(txn, room_id);
-
-            std::string_view temp;
-            // ensure we don't replace the event in the db
-            if (statesdb.get(txn, to_string(encr->type), temp)) {
-                return;
-            }
-        }
-
-        std::visit(
-          [&txn, &statesdb, &stateskeydb, &eventsDb, &membersdb](const auto &e) {
-              if constexpr (isStateEvent_<decltype(e)>) {
-                  eventsDb.put(txn, e.event_id, nlohmann::json(e).dump());
-
-                  if (e.type != EventType::Unsupported) {
-                      if (std::is_same_v<std::remove_cv_t<std::remove_reference_t<decltype(e)>>,
-                                         StateEvent<mtx::events::msg::Redacted>>) {
-                          // apply the redaction event
-                          if (e.type == EventType::RoomMember) {
-                              // membership is not revoked, but names are yeeted (so we set the name
-                              // to the mxid)
-                              MemberInfo tmp{e.state_key, ""};
-                              membersdb.put(txn, e.state_key, nlohmann::json(tmp).dump());
-                          } else if (e.state_key.empty()) {
-                              // strictly speaking some stuff in those events can be redacted, but
-                              // this is close enough. Ref:
-                              // https://spec.matrix.org/v1.6/rooms/v10/#redactions
-                              if (e.type != EventType::RoomCreate &&
-                                  e.type != EventType::RoomJoinRules &&
-                                  e.type != EventType::RoomPowerLevels &&
-                                  e.type != EventType::RoomHistoryVisibility)
-                                  statesdb.del(txn, to_string(e.type));
-                          } else
-                              stateskeydb.del(
-                                txn, to_string(e.type), e.state_key + '\0' + e.event_id);
-                      } else if (e.state_key.empty()) {
-                          statesdb.put(txn, to_string(e.type), nlohmann::json(e).dump());
-                      } else {
-                          auto data = e.state_key + '\0' + e.event_id;
-                          auto key  = to_string(e.type);
-
-                          // Work around https://bugs.openldap.org/show_bug.cgi?id=8447
-                          stateskeydb.del(txn, key, data);
-                          stateskeydb.put(txn, key, data);
-                      }
-                  }
-              }
-          },
-          event);
-    }
+                        const T &event);
 
     template<typename T>
     std::optional<mtx::events::StateEvent<T>>
-    getStateEvent(lmdb::txn &txn, const std::string &room_id, std::string_view state_key = "")
-    {
-        try {
-            constexpr auto type = mtx::events::state_content_to_type<T>;
-            static_assert(type != mtx::events::EventType::Unsupported,
-                          "Not a supported type in state events.");
-
-            if (room_id.empty())
-                return std::nullopt;
-            const auto typeStr = to_string(type);
-
-            std::string_view value;
-            if (state_key.empty()) {
-                auto db = getStatesDb(txn, room_id);
-                if (!db.get(txn, typeStr, value)) {
-                    return std::nullopt;
-                }
-            } else {
-                auto db = getStatesKeyDb(txn, room_id);
-                // we can search using state key, since the compare functions defaults to the whole
-                // string, when there is no nullbyte
-                std::string_view data     = state_key;
-                std::string_view typeStrV = typeStr;
-
-                auto cursor = lmdb::cursor::open(txn, db);
-                if (!cursor.get(typeStrV, data, MDB_GET_BOTH))
-                    return std::nullopt;
-
-                try {
-                    auto eventsDb = getEventsDb(txn, room_id);
-                    auto eventid  = data;
-                    if (auto sep = data.rfind('\0'); sep != std::string_view::npos) {
-                        if (!eventsDb.get(txn, eventid.substr(sep + 1), value))
-                            return std::nullopt;
-                    } else {
-                        return std::nullopt;
-                    }
-
-                } catch (std::exception &) {
-                    return std::nullopt;
-                }
-            }
-
-            return nlohmann::json::parse(value).get<mtx::events::StateEvent<T>>();
-        } catch (std::exception &) {
-            return std::nullopt;
-        }
-    }
+    getStateEvent(lmdb::txn &txn, const std::string &room_id, std::string_view state_key = "");
 
     template<typename T>
     std::vector<mtx::events::StateEvent<T>>
     getStateEventsWithType(lmdb::txn &txn,
                            const std::string &room_id,
-                           mtx::events::EventType type = mtx::events::state_content_to_type<T>)
+                           mtx::events::EventType type = mtx::events::state_content_to_type<T>);
 
-    {
-        if (room_id.empty())
-            return {};
-
-        std::vector<mtx::events::StateEvent<T>> events;
-
-        {
-            auto db                   = getStatesKeyDb(txn, room_id);
-            auto eventsDb             = getEventsDb(txn, room_id);
-            const auto typeStr        = to_string(type);
-            std::string_view typeStrV = typeStr;
-            std::string_view data;
-            std::string_view value;
-
-            auto cursor = lmdb::cursor::open(txn, db);
-            bool first  = true;
-            if (cursor.get(typeStrV, data, MDB_SET)) {
-                while (cursor.get(typeStrV, data, first ? MDB_FIRST_DUP : MDB_NEXT_DUP)) {
-                    first = false;
-
-                    try {
-                        auto eventid = data;
-                        if (auto sep = data.rfind('\0'); sep != std::string_view::npos) {
-                            if (eventsDb.get(txn, eventid.substr(sep + 1), value))
-                                events.push_back(
-                                  nlohmann::json::parse(value).get<mtx::events::StateEvent<T>>());
-                        }
-                    } catch (std::exception &e) {
-                        nhlog::db()->warn("Failed to parse state event: {}", e.what());
-                    }
-                }
-            }
-        }
-
-        return events;
-    }
     void
     saveInvites(lmdb::txn &txn, const std::map<std::string, mtx::responses::InvitedRoom> &rooms);
 
@@ -723,3 +542,33 @@ namespace cache {
 Cache *
 client();
 }
+
+#define NHEKO_CACHE_GET_STATE_EVENT_FORWARD(Content)                                               \
+    extern template std::optional<mtx::events::StateEvent<Content>> Cache::getStateEvent(          \
+      lmdb::txn &txn, const std::string &room_id, std::string_view state_key);                     \
+                                                                                                   \
+    extern template std::vector<mtx::events::StateEvent<Content>> Cache::getStateEventsWithType(   \
+      lmdb::txn &txn, const std::string &room_id, mtx::events::EventType type);
+
+NHEKO_CACHE_GET_STATE_EVENT_FORWARD(mtx::events::state::Aliases)
+NHEKO_CACHE_GET_STATE_EVENT_FORWARD(mtx::events::state::Avatar)
+NHEKO_CACHE_GET_STATE_EVENT_FORWARD(mtx::events::state::CanonicalAlias)
+NHEKO_CACHE_GET_STATE_EVENT_FORWARD(mtx::events::state::Create)
+NHEKO_CACHE_GET_STATE_EVENT_FORWARD(mtx::events::state::Encryption)
+NHEKO_CACHE_GET_STATE_EVENT_FORWARD(mtx::events::state::GuestAccess)
+NHEKO_CACHE_GET_STATE_EVENT_FORWARD(mtx::events::state::HistoryVisibility)
+NHEKO_CACHE_GET_STATE_EVENT_FORWARD(mtx::events::state::JoinRules)
+NHEKO_CACHE_GET_STATE_EVENT_FORWARD(mtx::events::state::Member)
+NHEKO_CACHE_GET_STATE_EVENT_FORWARD(mtx::events::state::Name)
+NHEKO_CACHE_GET_STATE_EVENT_FORWARD(mtx::events::state::PinnedEvents)
+NHEKO_CACHE_GET_STATE_EVENT_FORWARD(mtx::events::state::PowerLevels)
+NHEKO_CACHE_GET_STATE_EVENT_FORWARD(mtx::events::state::Tombstone)
+NHEKO_CACHE_GET_STATE_EVENT_FORWARD(mtx::events::state::ServerAcl)
+NHEKO_CACHE_GET_STATE_EVENT_FORWARD(mtx::events::state::Topic)
+NHEKO_CACHE_GET_STATE_EVENT_FORWARD(mtx::events::state::Widget)
+NHEKO_CACHE_GET_STATE_EVENT_FORWARD(mtx::events::state::policy_rule::UserRule)
+NHEKO_CACHE_GET_STATE_EVENT_FORWARD(mtx::events::state::policy_rule::RoomRule)
+NHEKO_CACHE_GET_STATE_EVENT_FORWARD(mtx::events::state::policy_rule::ServerRule)
+NHEKO_CACHE_GET_STATE_EVENT_FORWARD(mtx::events::state::space::Child)
+NHEKO_CACHE_GET_STATE_EVENT_FORWARD(mtx::events::state::space::Parent)
+NHEKO_CACHE_GET_STATE_EVENT_FORWARD(mtx::events::msc2545::ImagePack)