mirror of
https://github.com/uowuo/abaddon.git
synced 2024-11-10 14:10:10 +00:00
disk cache guild
This commit is contained in:
parent
b84a98fbb9
commit
bd918e7606
@ -382,8 +382,8 @@ void Abaddon::ActionInsertMention(Snowflake id) {
|
||||
|
||||
void Abaddon::ActionLeaveGuild(Snowflake id) {
|
||||
ConfirmDialog dlg(*m_main_window);
|
||||
const auto *guild = m_discord.GetGuild(id);
|
||||
if (guild != nullptr)
|
||||
const auto guild = m_discord.GetGuild(id);
|
||||
if (guild.has_value())
|
||||
dlg.SetConfirmText("Are you sure you want to leave " + guild->Name + "?");
|
||||
auto response = dlg.run();
|
||||
if (response == Gtk::RESPONSE_OK)
|
||||
|
@ -283,11 +283,11 @@ void ChannelList::UpdateRemoveChannel(Snowflake id) {
|
||||
// this is total shit
|
||||
void ChannelList::UpdateChannelCategory(Snowflake id) {
|
||||
const auto *data = Abaddon::Get().GetDiscordClient().GetChannel(id);
|
||||
const auto *guild = Abaddon::Get().GetDiscordClient().GetGuild(data->GuildID);
|
||||
const auto guild = Abaddon::Get().GetDiscordClient().GetGuild(data->GuildID);
|
||||
auto git = m_guild_id_to_row.find(data->GuildID);
|
||||
if (git == m_guild_id_to_row.end()) return;
|
||||
auto *guild_row = git->second;
|
||||
if (data == nullptr || guild == nullptr) return;
|
||||
if (data == nullptr || !guild.has_value()) return;
|
||||
auto it = m_id_to_row.find(id);
|
||||
if (it == m_id_to_row.end()) return;
|
||||
auto row = dynamic_cast<ChannelListRowCategory *>(it->second);
|
||||
@ -343,7 +343,7 @@ void ChannelList::UpdateChannelCategory(Snowflake id) {
|
||||
// so is this
|
||||
void ChannelList::UpdateChannel(Snowflake id) {
|
||||
const auto *data = Abaddon::Get().GetDiscordClient().GetChannel(id);
|
||||
const auto *guild = Abaddon::Get().GetDiscordClient().GetGuild(data->GuildID);
|
||||
const auto guild = Abaddon::Get().GetDiscordClient().GetGuild(data->GuildID);
|
||||
const auto *guild_row = m_guild_id_to_row.at(data->GuildID);
|
||||
if (data->Type == ChannelType::GUILD_CATEGORY) {
|
||||
UpdateChannelCategory(id);
|
||||
@ -402,7 +402,7 @@ void ChannelList::UpdateCreateChannel(Snowflake id) {
|
||||
UpdateCreateDMChannel(id);
|
||||
return;
|
||||
}
|
||||
const auto *guild = discord.GetGuild(data->GuildID);
|
||||
const auto guild = discord.GetGuild(data->GuildID);
|
||||
auto *guild_row = m_guild_id_to_row.at(data->GuildID);
|
||||
|
||||
int pos = guild_row->get_index() + 1;
|
||||
@ -437,8 +437,8 @@ void ChannelList::UpdateCreateChannel(Snowflake id) {
|
||||
|
||||
void ChannelList::UpdateGuild(Snowflake id) {
|
||||
// the only thing changed is the row containing the guild item so just recreate it
|
||||
const auto *data = Abaddon::Get().GetDiscordClient().GetGuild(id);
|
||||
if (data == nullptr) return;
|
||||
const auto data = Abaddon::Get().GetDiscordClient().GetGuild(id);
|
||||
if (!data.has_value()) return;
|
||||
auto it = m_guild_id_to_row.find(id);
|
||||
if (it == m_guild_id_to_row.end()) return;
|
||||
auto *row = dynamic_cast<ChannelListRowGuild *>(it->second);
|
||||
@ -447,7 +447,7 @@ void ChannelList::UpdateGuild(Snowflake id) {
|
||||
const bool old_collapsed = row->IsUserCollapsed;
|
||||
const bool old_gindex = row->GuildIndex;
|
||||
delete row;
|
||||
auto *new_row = Gtk::manage(new ChannelListRowGuild(data));
|
||||
auto *new_row = Gtk::manage(new ChannelListRowGuild(&*data));
|
||||
new_row->IsUserCollapsed = old_collapsed;
|
||||
new_row->GuildIndex = old_gindex;
|
||||
m_guild_id_to_row[new_row->ID] = new_row;
|
||||
@ -523,21 +523,24 @@ void ChannelList::InsertGuildAt(Snowflake id, int pos) {
|
||||
};
|
||||
|
||||
const auto &discord = Abaddon::Get().GetDiscordClient();
|
||||
const auto *guild_data = discord.GetGuild(id);
|
||||
if (guild_data == nullptr) return;
|
||||
const auto guild_data = discord.GetGuild(id);
|
||||
if (!guild_data.has_value()) return;
|
||||
|
||||
std::map<int, const Channel *> orphan_channels;
|
||||
std::unordered_map<Snowflake, std::vector<const Channel *>> cat_to_channels;
|
||||
for (const auto &channel : guild_data->Channels) {
|
||||
if (channel.Type != ChannelType::GUILD_TEXT && channel.Type != ChannelType::GUILD_NEWS) continue;
|
||||
if (guild_data->Channels.has_value())
|
||||
for (const auto &dc : *guild_data->Channels) {
|
||||
const auto channel = discord.GetChannel(dc.ID);
|
||||
if (channel == nullptr) continue;
|
||||
if (channel->Type != ChannelType::GUILD_TEXT && channel->Type != ChannelType::GUILD_NEWS) continue;
|
||||
|
||||
if (channel.ParentID.IsValid())
|
||||
cat_to_channels[channel.ParentID].push_back(&channel);
|
||||
else
|
||||
orphan_channels[channel.Position] = &channel;
|
||||
}
|
||||
if (channel->ParentID.IsValid())
|
||||
cat_to_channels[channel->ParentID].push_back(&*channel);
|
||||
else
|
||||
orphan_channels[channel->Position] = &*channel;
|
||||
}
|
||||
|
||||
auto *guild_row = Gtk::manage(new ChannelListRowGuild(guild_data));
|
||||
auto *guild_row = Gtk::manage(new ChannelListRowGuild(&*guild_data));
|
||||
guild_row->show_all();
|
||||
guild_row->IsUserCollapsed = true;
|
||||
guild_row->GuildIndex = m_guild_count++;
|
||||
@ -558,9 +561,13 @@ void ChannelList::InsertGuildAt(Snowflake id, int pos) {
|
||||
|
||||
// categories
|
||||
std::map<int, std::vector<const Channel *>> sorted_categories;
|
||||
for (const auto &channel : guild_data->Channels)
|
||||
if (channel.Type == ChannelType::GUILD_CATEGORY)
|
||||
sorted_categories[channel.Position].push_back(&channel);
|
||||
if (guild_data->Channels.has_value())
|
||||
for (const auto &dc : *guild_data->Channels) {
|
||||
const auto channel = discord.GetChannel(dc.ID);
|
||||
if (channel == nullptr) continue;
|
||||
if (channel->Type == ChannelType::GUILD_CATEGORY)
|
||||
sorted_categories[channel->Position].push_back(&*channel);
|
||||
}
|
||||
|
||||
for (auto &[pos, catvec] : sorted_categories) {
|
||||
std::sort(catvec.begin(), catvec.end(), [](const Channel *a, const Channel *b) { return a->ID < b->ID; });
|
||||
@ -619,7 +626,7 @@ void ChannelList::AddPrivateChannels() {
|
||||
}
|
||||
|
||||
void ChannelList::UpdateListingInternal() {
|
||||
std::unordered_set<Snowflake> guilds = Abaddon::Get().GetDiscordClient().GetGuildsID();
|
||||
std::unordered_set<Snowflake> guilds = Abaddon::Get().GetDiscordClient().GetGuilds();
|
||||
|
||||
auto children = m_list->get_children();
|
||||
auto it = children.begin();
|
||||
|
@ -52,22 +52,14 @@ bool DiscordClient::IsStoreValid() const {
|
||||
return m_store.IsValid();
|
||||
}
|
||||
|
||||
std::unordered_set<Snowflake> DiscordClient::GetGuildsID() const {
|
||||
const auto &guilds = m_store.GetGuilds();
|
||||
std::unordered_set<Snowflake> ret;
|
||||
for (const auto &[gid, data] : guilds)
|
||||
ret.insert(gid);
|
||||
return ret;
|
||||
}
|
||||
|
||||
const Store::guilds_type &DiscordClient::GetGuilds() const {
|
||||
return m_store.GetGuilds();
|
||||
}
|
||||
|
||||
const UserSettings &DiscordClient::GetUserSettings() const {
|
||||
return m_user_settings;
|
||||
}
|
||||
|
||||
std::unordered_set<Snowflake> DiscordClient::GetGuilds() const {
|
||||
return m_store.GetGuilds();
|
||||
}
|
||||
|
||||
const User &DiscordClient::GetUserData() const {
|
||||
return m_user_data;
|
||||
}
|
||||
@ -76,7 +68,7 @@ std::vector<Snowflake> DiscordClient::GetUserSortedGuilds() const {
|
||||
// sort order is unfolder'd guilds sorted by id descending, then guilds in folders in array order
|
||||
// todo: make sure folder'd guilds are sorted properly
|
||||
std::vector<Snowflake> folder_order;
|
||||
auto guilds = GetGuildsID();
|
||||
auto guilds = GetGuilds();
|
||||
for (const auto &entry : m_user_settings.GuildFolders) { // can contain guilds not a part of
|
||||
for (const auto &id : entry.GuildIDs) {
|
||||
if (std::find(guilds.begin(), guilds.end(), id) != guilds.end())
|
||||
@ -181,7 +173,7 @@ std::optional<Role> DiscordClient::GetRole(Snowflake id) const {
|
||||
return m_store.GetRole(id);
|
||||
}
|
||||
|
||||
const Guild *DiscordClient::GetGuild(Snowflake id) const {
|
||||
std::optional<Guild> DiscordClient::GetGuild(Snowflake id) const {
|
||||
return m_store.GetGuild(id);
|
||||
}
|
||||
|
||||
@ -264,8 +256,8 @@ bool DiscordClient::HasChannelPermission(Snowflake user_id, Snowflake channel_id
|
||||
|
||||
Permission DiscordClient::ComputePermissions(Snowflake member_id, Snowflake guild_id) const {
|
||||
const auto member = GetMember(member_id, guild_id);
|
||||
const auto *guild = GetGuild(guild_id);
|
||||
if (!member.has_value() || guild == nullptr)
|
||||
const auto guild = GetGuild(guild_id);
|
||||
if (!member.has_value() || !guild.has_value())
|
||||
return Permission::NONE;
|
||||
|
||||
if (guild->OwnerID == member_id)
|
||||
@ -327,8 +319,8 @@ Permission DiscordClient::ComputeOverwrites(Permission base, Snowflake member_id
|
||||
}
|
||||
|
||||
bool DiscordClient::CanManageMember(Snowflake guild_id, Snowflake actor, Snowflake target) const {
|
||||
const auto *guild = GetGuild(guild_id);
|
||||
if (guild != nullptr && guild->OwnerID == target) return false;
|
||||
const auto guild = GetGuild(guild_id);
|
||||
if (guild.has_value() && guild->OwnerID == target) return false;
|
||||
const auto actor_highest_id = GetMemberHighestRole(guild_id, actor);
|
||||
const auto target_highest_id = GetMemberHighestRole(guild_id, target);
|
||||
const auto actor_highest = GetRole(actor_highest_id);
|
||||
@ -582,14 +574,15 @@ void DiscordClient::ProcessNewGuild(Guild &guild) {
|
||||
m_store.BeginTransaction();
|
||||
|
||||
m_store.SetGuild(guild.ID, guild);
|
||||
for (auto &c : guild.Channels) {
|
||||
c.GuildID = guild.ID;
|
||||
m_store.SetChannel(c.ID, c);
|
||||
m_guild_to_channels[guild.ID].insert(c.ID);
|
||||
for (auto &p : c.PermissionOverwrites) {
|
||||
m_store.SetPermissionOverwrite(c.ID, p.ID, p);
|
||||
if (guild.Channels.has_value())
|
||||
for (auto &c : *guild.Channels) {
|
||||
c.GuildID = guild.ID;
|
||||
m_store.SetChannel(c.ID, c);
|
||||
m_guild_to_channels[guild.ID].insert(c.ID);
|
||||
for (auto &p : c.PermissionOverwrites) {
|
||||
m_store.SetPermissionOverwrite(c.ID, p.ID, p);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
for (auto &r : guild.Roles)
|
||||
m_store.SetRole(r.ID, r);
|
||||
@ -702,8 +695,8 @@ void DiscordClient::HandleGatewayChannelCreate(const GatewayMessage &msg) {
|
||||
|
||||
void DiscordClient::HandleGatewayGuildUpdate(const GatewayMessage &msg) {
|
||||
Snowflake id = msg.Data.at("id");
|
||||
auto *current = m_store.GetGuild(id);
|
||||
if (current == nullptr) return;
|
||||
auto current = m_store.GetGuild(id);
|
||||
if (!current.has_value()) return;
|
||||
current->update_from_json(msg.Data);
|
||||
m_signal_guild_update.emit(id);
|
||||
}
|
||||
@ -780,16 +773,17 @@ void DiscordClient::HandleGatewayGuildDelete(const GatewayMessage &msg) {
|
||||
if (unavailable)
|
||||
printf("guild %llu became unavailable\n", static_cast<uint64_t>(id));
|
||||
|
||||
auto *guild = m_store.GetGuild(id);
|
||||
if (guild == nullptr) {
|
||||
const auto guild = m_store.GetGuild(id);
|
||||
if (!guild.has_value()) {
|
||||
m_store.ClearGuild(id);
|
||||
m_signal_guild_delete.emit(id);
|
||||
return;
|
||||
}
|
||||
|
||||
m_store.ClearGuild(id);
|
||||
for (const auto &c : guild->Channels)
|
||||
m_store.ClearChannel(c.ID);
|
||||
if (guild->Channels.has_value())
|
||||
for (const auto &c : *guild->Channels)
|
||||
m_store.ClearChannel(c.ID);
|
||||
|
||||
m_signal_guild_delete.emit(id);
|
||||
}
|
||||
|
@ -69,8 +69,7 @@ public:
|
||||
using members_type = Store::members_type;
|
||||
using permission_overwrites_type = Store::permission_overwrites_type;
|
||||
|
||||
std::unordered_set<Snowflake> GetGuildsID() const;
|
||||
const guilds_type &GetGuilds() const;
|
||||
std::unordered_set<Snowflake> GetGuilds() const;
|
||||
const User &GetUserData() const;
|
||||
const UserSettings &GetUserSettings() const;
|
||||
std::vector<Snowflake> GetUserSortedGuilds() const;
|
||||
@ -86,7 +85,7 @@ public:
|
||||
std::optional<PermissionOverwrite> GetPermissionOverwrite(Snowflake channel_id, Snowflake id) const;
|
||||
std::optional<User> GetUser(Snowflake id) const;
|
||||
std::optional<Role> GetRole(Snowflake id) const;
|
||||
const Guild *GetGuild(Snowflake id) const;
|
||||
std::optional<Guild> GetGuild(Snowflake id) const;
|
||||
std::optional<GuildMember> GetMember(Snowflake user_id, Snowflake guild_id) const;
|
||||
Snowflake GetMemberHoistedRole(Snowflake guild_id, Snowflake user_id, bool with_color = false) const;
|
||||
Snowflake GetMemberHighestRole(Snowflake guild_id, Snowflake user_id) const;
|
||||
|
@ -56,10 +56,10 @@ void from_json(const nlohmann::json &j, Guild &m) {
|
||||
JS_O("max_video_channel_users", m.MaxVideoChannelUsers);
|
||||
JS_O("approximate_member_count", tmp);
|
||||
if (tmp.has_value())
|
||||
m.ApproximateMemberCount = std::stoull(*tmp);
|
||||
m.ApproximateMemberCount = std::stol(*tmp);
|
||||
JS_O("approximate_presence_count", tmp);
|
||||
if (tmp.has_value())
|
||||
m.ApproximatePresenceCount = std::stoull(*tmp);
|
||||
m.ApproximatePresenceCount = std::stol(*tmp);
|
||||
}
|
||||
|
||||
void Guild::update_from_json(const nlohmann::json &j) {
|
||||
|
@ -10,53 +10,53 @@
|
||||
// a bot is apparently only supposed to receive the `id` and `unavailable` as false
|
||||
// but user tokens seem to get the full objects (minus users)
|
||||
struct Guild {
|
||||
Snowflake ID; //
|
||||
std::string Name; //
|
||||
std::string Icon; // null
|
||||
std::string Splash; // null
|
||||
std::string DiscoverySplash; // opt, null (docs wrong)
|
||||
bool IsOwner = false; // opt
|
||||
Snowflake OwnerID; //
|
||||
int Permissions = 0; // opt
|
||||
std::string PermissionsNew; // opt
|
||||
std::string VoiceRegion; // opt
|
||||
Snowflake AFKChannelID; // null
|
||||
int AFKTimeout; //
|
||||
bool IsEmbedEnabled = false; // opt, deprecated
|
||||
Snowflake EmbedChannelID; // opt, null, deprecated
|
||||
int VerificationLevel; //
|
||||
int DefaultMessageNotifications; //
|
||||
int ExplicitContentFilter; //
|
||||
std::vector<Role> Roles; //
|
||||
std::vector<Emoji> Emojis; //
|
||||
std::vector<std::string> Features; //
|
||||
int MFALevel; //
|
||||
Snowflake ApplicationID; // null
|
||||
bool IsWidgetEnabled = false; // opt
|
||||
Snowflake WidgetChannelID; // opt, null
|
||||
Snowflake SystemChannelID; // null
|
||||
int SystemChannelFlags; //
|
||||
Snowflake RulesChannelID; // null
|
||||
std::string JoinedAt; // opt*
|
||||
bool IsLarge = false; // opt*
|
||||
bool IsUnavailable = false; // opt*
|
||||
int MemberCount = 0; // opt*
|
||||
Snowflake ID;
|
||||
std::string Name;
|
||||
std::string Icon; // null
|
||||
std::string Splash; // null
|
||||
std::optional<std::string> DiscoverySplash; // null
|
||||
std::optional<bool> IsOwner;
|
||||
Snowflake OwnerID;
|
||||
std::optional<uint64_t> Permissions;
|
||||
std::optional<std::string> PermissionsNew;
|
||||
std::optional<std::string> VoiceRegion;
|
||||
Snowflake AFKChannelID; // null
|
||||
int AFKTimeout;
|
||||
std::optional<bool> IsEmbedEnabled; // deprecated
|
||||
std::optional<Snowflake> EmbedChannelID; // null, deprecated
|
||||
int VerificationLevel;
|
||||
int DefaultMessageNotifications;
|
||||
int ExplicitContentFilter;
|
||||
std::vector<Role> Roles; // only access id
|
||||
std::vector<Emoji> Emojis; // only access id
|
||||
std::vector<std::string> Features;
|
||||
int MFALevel;
|
||||
Snowflake ApplicationID; // null
|
||||
std::optional<bool> IsWidgetEnabled;
|
||||
std::optional<Snowflake> WidgetChannelID; // null
|
||||
Snowflake SystemChannelID; // null
|
||||
int SystemChannelFlags;
|
||||
Snowflake RulesChannelID; // null
|
||||
std::optional<std::string> JoinedAt; // *
|
||||
std::optional<bool> IsLarge; // *
|
||||
std::optional<bool> IsUnavailable; // *
|
||||
std::optional<int> MemberCount; // *
|
||||
// std::vector<VoiceStateData> VoiceStates; // opt*
|
||||
// std::vector<MemberData> Members; // opt* - incomplete anyways
|
||||
std::vector<Channel> Channels; // opt*
|
||||
std::optional<std::vector<Channel>> Channels; // *
|
||||
// std::vector<PresenceUpdateData> Presences; // opt*
|
||||
int MaxPresences = 0; // opt, null
|
||||
int MaxMembers = 0; // opt
|
||||
std::string VanityURL; // null
|
||||
std::string Description; // null
|
||||
std::string BannerHash; // null
|
||||
int PremiumTier; //
|
||||
int PremiumSubscriptionCount = 0; // opt
|
||||
std::string PreferredLocale; //
|
||||
std::optional<int> MaxPresences; // null
|
||||
std::optional<int> MaxMembers;
|
||||
std::string VanityURL; // null
|
||||
std::string Description; // null
|
||||
std::string BannerHash; // null
|
||||
int PremiumTier;
|
||||
std::optional<int> PremiumSubscriptionCount;
|
||||
std::string PreferredLocale;
|
||||
Snowflake PublicUpdatesChannelID; // null
|
||||
int MaxVideoChannelUsers = 0; // opt
|
||||
int ApproximateMemberCount = 0; // opt
|
||||
int ApproximatePresenceCount = 0; // opt
|
||||
std::optional<int> MaxVideoChannelUsers;
|
||||
std::optional<int> ApproximateMemberCount;
|
||||
std::optional<int> ApproximatePresenceCount;
|
||||
|
||||
// undocumented
|
||||
// std::map<std::string, Unknown> GuildHashes;
|
||||
|
@ -76,7 +76,59 @@ void Store::SetChannel(Snowflake id, const Channel &channel) {
|
||||
}
|
||||
|
||||
void Store::SetGuild(Snowflake id, const Guild &guild) {
|
||||
m_guilds[id] = guild;
|
||||
Bind(m_set_guild_stmt, 1, id);
|
||||
Bind(m_set_guild_stmt, 2, guild.Name);
|
||||
Bind(m_set_guild_stmt, 3, guild.Icon);
|
||||
Bind(m_set_guild_stmt, 4, guild.Splash);
|
||||
Bind(m_set_guild_stmt, 5, guild.IsOwner);
|
||||
Bind(m_set_guild_stmt, 6, guild.OwnerID);
|
||||
Bind(m_set_guild_stmt, 7, guild.PermissionsNew);
|
||||
Bind(m_set_guild_stmt, 8, guild.VoiceRegion);
|
||||
Bind(m_set_guild_stmt, 9, guild.AFKChannelID);
|
||||
Bind(m_set_guild_stmt, 10, guild.AFKTimeout);
|
||||
Bind(m_set_guild_stmt, 11, guild.VerificationLevel);
|
||||
Bind(m_set_guild_stmt, 12, guild.DefaultMessageNotifications);
|
||||
std::vector<Snowflake> snowflakes;
|
||||
for (const auto &x : guild.Roles) snowflakes.push_back(x.ID);
|
||||
Bind(m_set_guild_stmt, 13, nlohmann::json(snowflakes).dump());
|
||||
snowflakes.clear();
|
||||
for (const auto &x : guild.Emojis) snowflakes.push_back(x.ID);
|
||||
Bind(m_set_guild_stmt, 14, nlohmann::json(snowflakes).dump());
|
||||
Bind(m_set_guild_stmt, 15, nlohmann::json(guild.Features).dump());
|
||||
Bind(m_set_guild_stmt, 16, guild.MFALevel);
|
||||
Bind(m_set_guild_stmt, 17, guild.ApplicationID);
|
||||
Bind(m_set_guild_stmt, 18, guild.IsWidgetEnabled);
|
||||
Bind(m_set_guild_stmt, 19, guild.WidgetChannelID);
|
||||
Bind(m_set_guild_stmt, 20, guild.SystemChannelFlags);
|
||||
Bind(m_set_guild_stmt, 21, guild.RulesChannelID);
|
||||
Bind(m_set_guild_stmt, 22, guild.JoinedAt);
|
||||
Bind(m_set_guild_stmt, 23, guild.IsLarge);
|
||||
Bind(m_set_guild_stmt, 24, guild.IsUnavailable);
|
||||
Bind(m_set_guild_stmt, 25, guild.MemberCount);
|
||||
if (guild.Channels.has_value()) {
|
||||
snowflakes.clear();
|
||||
for (const auto &x : *guild.Channels) snowflakes.push_back(x.ID);
|
||||
Bind(m_set_guild_stmt, 26, nlohmann::json(snowflakes).dump());
|
||||
} else
|
||||
Bind(m_set_guild_stmt, 26, "[]"s);
|
||||
Bind(m_set_guild_stmt, 27, guild.MaxPresences);
|
||||
Bind(m_set_guild_stmt, 28, guild.MaxMembers);
|
||||
Bind(m_set_guild_stmt, 29, guild.VanityURL);
|
||||
Bind(m_set_guild_stmt, 30, guild.Description);
|
||||
Bind(m_set_guild_stmt, 31, guild.BannerHash);
|
||||
Bind(m_set_guild_stmt, 32, guild.PremiumTier);
|
||||
Bind(m_set_guild_stmt, 33, guild.PremiumSubscriptionCount);
|
||||
Bind(m_set_guild_stmt, 34, guild.PreferredLocale);
|
||||
Bind(m_set_guild_stmt, 35, guild.PublicUpdatesChannelID);
|
||||
Bind(m_set_guild_stmt, 36, guild.MaxVideoChannelUsers);
|
||||
Bind(m_set_guild_stmt, 37, guild.ApproximateMemberCount);
|
||||
Bind(m_set_guild_stmt, 38, guild.ApproximatePresenceCount);
|
||||
Bind(m_set_guild_stmt, 39, guild.IsLazy);
|
||||
|
||||
if (!RunInsert(m_set_guild_stmt))
|
||||
fprintf(stderr, "guild insert failed: %s\n", sqlite3_errstr(m_db_err));
|
||||
|
||||
m_guilds.insert(id);
|
||||
}
|
||||
|
||||
void Store::SetRole(Snowflake id, const Role &role) {
|
||||
@ -150,7 +202,7 @@ void Store::SetGuildMember(Snowflake guild_id, Snowflake user_id, const GuildMem
|
||||
Bind(m_set_member_stmt, 6, data.PremiumSince);
|
||||
Bind(m_set_member_stmt, 7, data.IsDeafened);
|
||||
Bind(m_set_member_stmt, 8, data.IsMuted);
|
||||
|
||||
|
||||
if (!RunInsert(m_set_member_stmt))
|
||||
fprintf(stderr, "member insert failed: %s\n", sqlite3_errstr(m_db_err));
|
||||
}
|
||||
@ -216,6 +268,70 @@ std::optional<Emoji> Store::GetEmoji(Snowflake id) const {
|
||||
return ret;
|
||||
}
|
||||
|
||||
std::optional<Guild> Store::GetGuild(Snowflake id) const {
|
||||
Bind(m_get_guild_stmt, 1, id);
|
||||
if (!FetchOne(m_get_guild_stmt)) {
|
||||
if (m_db_err != SQLITE_DONE)
|
||||
fprintf(stderr, "error while fetching guild: %s\n", sqlite3_errstr(m_db_err));
|
||||
Reset(m_get_guild_stmt);
|
||||
return std::nullopt;
|
||||
}
|
||||
|
||||
Guild ret;
|
||||
ret.ID = id;
|
||||
Get(m_get_guild_stmt, 1, ret.Name);
|
||||
Get(m_get_guild_stmt, 2, ret.Icon);
|
||||
Get(m_get_guild_stmt, 3, ret.Splash);
|
||||
Get(m_get_guild_stmt, 4, ret.IsOwner);
|
||||
Get(m_get_guild_stmt, 5, ret.OwnerID);
|
||||
Get(m_get_guild_stmt, 6, ret.PermissionsNew);
|
||||
Get(m_get_guild_stmt, 7, ret.VoiceRegion);
|
||||
Get(m_get_guild_stmt, 8, ret.AFKChannelID);
|
||||
Get(m_get_guild_stmt, 9, ret.AFKTimeout);
|
||||
Get(m_get_guild_stmt, 10, ret.VerificationLevel);
|
||||
Get(m_get_guild_stmt, 11, ret.DefaultMessageNotifications);
|
||||
std::string tmp;
|
||||
Get(m_get_guild_stmt, 12, tmp);
|
||||
for (const auto &id : nlohmann::json::parse(tmp).get<std::vector<Snowflake>>())
|
||||
ret.Roles.emplace_back().ID = id;
|
||||
Get(m_get_guild_stmt, 13, tmp);
|
||||
for (const auto &id : nlohmann::json::parse(tmp).get<std::vector<Snowflake>>())
|
||||
ret.Emojis.emplace_back().ID = id;
|
||||
Get(m_get_guild_stmt, 14, tmp);
|
||||
ret.Features = nlohmann::json::parse(tmp).get<std::vector<std::string>>();
|
||||
Get(m_get_guild_stmt, 15, ret.MFALevel);
|
||||
Get(m_get_guild_stmt, 16, ret.ApplicationID);
|
||||
Get(m_get_guild_stmt, 17, ret.IsWidgetEnabled);
|
||||
Get(m_get_guild_stmt, 18, ret.WidgetChannelID);
|
||||
Get(m_get_guild_stmt, 19, ret.SystemChannelFlags);
|
||||
Get(m_get_guild_stmt, 20, ret.RulesChannelID);
|
||||
Get(m_get_guild_stmt, 21, ret.JoinedAt);
|
||||
Get(m_get_guild_stmt, 22, ret.IsLarge);
|
||||
Get(m_get_guild_stmt, 23, ret.IsUnavailable);
|
||||
Get(m_get_guild_stmt, 24, ret.MemberCount);
|
||||
Get(m_get_guild_stmt, 25, tmp);
|
||||
ret.Channels.emplace();
|
||||
for (const auto &id : nlohmann::json::parse(tmp).get<std::vector<Snowflake>>())
|
||||
ret.Channels->emplace_back().ID = id;
|
||||
Get(m_get_guild_stmt, 26, ret.MaxPresences);
|
||||
Get(m_get_guild_stmt, 27, ret.MaxMembers);
|
||||
Get(m_get_guild_stmt, 28, ret.VanityURL);
|
||||
Get(m_get_guild_stmt, 29, ret.Description);
|
||||
Get(m_get_guild_stmt, 30, ret.BannerHash);
|
||||
Get(m_get_guild_stmt, 31, ret.PremiumTier);
|
||||
Get(m_get_guild_stmt, 32, ret.PremiumSubscriptionCount);
|
||||
Get(m_get_guild_stmt, 33, ret.PreferredLocale);
|
||||
Get(m_get_guild_stmt, 34, ret.PublicUpdatesChannelID);
|
||||
Get(m_get_guild_stmt, 35, ret.MaxVideoChannelUsers);
|
||||
Get(m_get_guild_stmt, 36, ret.ApproximateMemberCount);
|
||||
Get(m_get_guild_stmt, 37, ret.ApproximatePresenceCount);
|
||||
Get(m_get_guild_stmt, 38, ret.IsLazy);
|
||||
|
||||
Reset(m_get_guild_stmt);
|
||||
|
||||
return ret;
|
||||
}
|
||||
|
||||
std::optional<GuildMember> Store::GetGuildMember(Snowflake guild_id, Snowflake user_id) const {
|
||||
Bind(m_get_member_stmt, 1, guild_id);
|
||||
Bind(m_get_member_stmt, 2, user_id);
|
||||
@ -386,20 +502,6 @@ const Channel *Store::GetChannel(Snowflake id) const {
|
||||
return &it->second;
|
||||
}
|
||||
|
||||
Guild *Store::GetGuild(Snowflake id) {
|
||||
auto it = m_guilds.find(id);
|
||||
if (it == m_guilds.end())
|
||||
return nullptr;
|
||||
return &it->second;
|
||||
}
|
||||
|
||||
const Guild *Store::GetGuild(Snowflake id) const {
|
||||
auto it = m_guilds.find(id);
|
||||
if (it == m_guilds.end())
|
||||
return nullptr;
|
||||
return &it->second;
|
||||
}
|
||||
|
||||
void Store::ClearGuild(Snowflake id) {
|
||||
m_guilds.erase(id);
|
||||
}
|
||||
@ -412,13 +514,12 @@ const Store::channels_type &Store::GetChannels() const {
|
||||
return m_channels;
|
||||
}
|
||||
|
||||
const Store::guilds_type &Store::GetGuilds() const {
|
||||
const std::unordered_set<Snowflake> &Store::GetGuilds() const {
|
||||
return m_guilds;
|
||||
}
|
||||
void Store::ClearAll() {
|
||||
m_channels.clear();
|
||||
m_guilds.clear();
|
||||
m_members.clear();
|
||||
}
|
||||
|
||||
void Store::BeginTransaction() {
|
||||
@ -521,6 +622,50 @@ premium_since TEXT,
|
||||
deaf BOOL NOT NULL,
|
||||
mute BOOL NOT NULL
|
||||
)
|
||||
)";
|
||||
|
||||
constexpr char *create_guilds = R"(
|
||||
CREATE TABLE IF NOT EXISTS guilds (
|
||||
id INTEGER PRIMARY KEY,
|
||||
name TEXT NOT NULL,
|
||||
icon TEXT NOT NULL,
|
||||
splash TEXT,
|
||||
owner BOOL,
|
||||
owner_id INTEGER NOT NULL,
|
||||
permissions INTEGER, /* new */
|
||||
voice_region TEXT,
|
||||
afk_id INTEGER,
|
||||
afk_timeout INTEGER NOT NULL,
|
||||
verification INTEGER NOT NULL,
|
||||
notifications INTEGER NOT NULL,
|
||||
roles TEXT NOT NULL, /* json */
|
||||
emojis TEXT NOT NULL, /* json */
|
||||
features TEXT NOT NULL, /* json */
|
||||
mfa INTEGER NOT NULL,
|
||||
application INTEGER,
|
||||
widget BOOL,
|
||||
widget_channel INTEGER,
|
||||
system_flags INTEGER NOT NULL,
|
||||
rules_channel INTEGER,
|
||||
joined_at TEXT,
|
||||
large BOOL,
|
||||
unavailable BOOL,
|
||||
member_count INTEGER,
|
||||
channels TEXT NOT NULL, /* json */
|
||||
max_presences INTEGER,
|
||||
max_members INTEGER,
|
||||
vanity TEXT,
|
||||
description TEXT,
|
||||
banner_hash TEXT,
|
||||
premium_tier INTEGER NOT NULL,
|
||||
premium_count INTEGER,
|
||||
locale TEXT NOT NULL,
|
||||
public_updates_id INTEGER,
|
||||
max_video_users INTEGER,
|
||||
approx_members INTEGER,
|
||||
approx_presences INTEGER,
|
||||
lazy BOOL
|
||||
)
|
||||
)";
|
||||
|
||||
m_db_err = sqlite3_exec(m_db, create_users, nullptr, nullptr, nullptr);
|
||||
@ -559,6 +704,12 @@ mute BOOL NOT NULL
|
||||
return false;
|
||||
}
|
||||
|
||||
m_db_err = sqlite3_exec(m_db, create_guilds, nullptr, nullptr, nullptr);
|
||||
if (m_db_err != SQLITE_OK) {
|
||||
fprintf(stderr, "failed to create guilds table: %s\n", sqlite3_errstr(m_db_err));
|
||||
return false;
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
@ -621,6 +772,16 @@ REPLACE INTO members VALUES (
|
||||
|
||||
constexpr const char *get_member = R"(
|
||||
SELECT * FROM members WHERE user_id = ? AND guild_id = ?
|
||||
)";
|
||||
|
||||
constexpr const char *set_guild = R"(
|
||||
REPLACE INTO guilds VALUES (
|
||||
?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?
|
||||
)
|
||||
)";
|
||||
|
||||
constexpr const char *get_guild = R"(
|
||||
SELECT * FROM guilds WHERE id = ?
|
||||
)";
|
||||
|
||||
m_db_err = sqlite3_prepare_v2(m_db, set_user, -1, &m_set_user_stmt, nullptr);
|
||||
@ -695,6 +856,18 @@ SELECT * FROM members WHERE user_id = ? AND guild_id = ?
|
||||
return false;
|
||||
}
|
||||
|
||||
m_db_err = sqlite3_prepare_v2(m_db, set_guild, -1, &m_set_guild_stmt, nullptr);
|
||||
if (m_db_err != SQLITE_OK) {
|
||||
fprintf(stderr, "failed to prepare set guild statement: %s\n", sqlite3_errstr(m_db_err));
|
||||
return false;
|
||||
}
|
||||
|
||||
m_db_err = sqlite3_prepare_v2(m_db, get_guild, -1, &m_get_guild_stmt, nullptr);
|
||||
if (m_db_err != SQLITE_OK) {
|
||||
fprintf(stderr, "failed to prepare get guild statement: %s\n", sqlite3_errstr(m_db_err));
|
||||
return false;
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
@ -711,6 +884,8 @@ void Store::Cleanup() {
|
||||
sqlite3_finalize(m_get_emote_stmt);
|
||||
sqlite3_finalize(m_set_member_stmt);
|
||||
sqlite3_finalize(m_get_member_stmt);
|
||||
sqlite3_finalize(m_set_guild_stmt);
|
||||
sqlite3_finalize(m_get_guild_stmt);
|
||||
}
|
||||
|
||||
void Store::Bind(sqlite3_stmt *stmt, int index, int num) const {
|
||||
|
@ -2,6 +2,7 @@
|
||||
#include "../util.hpp"
|
||||
#include "objects.hpp"
|
||||
#include <unordered_map>
|
||||
#include <unordered_set>
|
||||
#include <mutex>
|
||||
#include <filesystem>
|
||||
#include <sqlite3.h>
|
||||
@ -29,15 +30,14 @@ public:
|
||||
// slap const on everything even tho its not *really* const
|
||||
|
||||
Channel *GetChannel(Snowflake id);
|
||||
Guild *GetGuild(Snowflake id);
|
||||
std::optional<Emoji> GetEmoji(Snowflake id) const;
|
||||
std::optional<Guild> GetGuild(Snowflake id) const;
|
||||
std::optional<GuildMember> GetGuildMember(Snowflake guild_id, Snowflake user_id) const;
|
||||
std::optional<Message> GetMessage(Snowflake id) const;
|
||||
std::optional<PermissionOverwrite> GetPermissionOverwrite(Snowflake channel_id, Snowflake id) const;
|
||||
std::optional<Role> GetRole(Snowflake id) const;
|
||||
std::optional<User> GetUser(Snowflake id) const;
|
||||
const Channel *GetChannel(Snowflake id) const;
|
||||
const Guild *GetGuild(Snowflake id) const;
|
||||
|
||||
void ClearGuild(Snowflake id);
|
||||
void ClearChannel(Snowflake id);
|
||||
@ -52,7 +52,7 @@ public:
|
||||
using emojis_type = std::unordered_map<Snowflake, Emoji>;
|
||||
|
||||
const channels_type &GetChannels() const;
|
||||
const guilds_type &GetGuilds() const;
|
||||
const std::unordered_set<Snowflake> &GetGuilds() const;
|
||||
|
||||
void ClearAll();
|
||||
|
||||
@ -61,8 +61,7 @@ public:
|
||||
|
||||
private:
|
||||
channels_type m_channels;
|
||||
guilds_type m_guilds;
|
||||
members_type m_members;
|
||||
std::unordered_set<Snowflake> m_guilds;
|
||||
|
||||
bool CreateTables();
|
||||
bool CreateStatements();
|
||||
@ -101,6 +100,8 @@ private:
|
||||
mutable sqlite3_stmt *m_get_emote_stmt;
|
||||
mutable sqlite3_stmt *m_set_member_stmt;
|
||||
mutable sqlite3_stmt *m_get_member_stmt;
|
||||
mutable sqlite3_stmt *m_set_guild_stmt;
|
||||
mutable sqlite3_stmt *m_get_guild_stmt;
|
||||
};
|
||||
|
||||
template<typename T>
|
||||
|
Loading…
Reference in New Issue
Block a user