From 17be2bf2f77dc1bbb7dabfcc05bbd1fe56f5df03 Mon Sep 17 00:00:00 2001 From: hg <4683435+hgtw@users.noreply.github.com> Date: Sat, 13 Jun 2020 21:28:21 -0400 Subject: [PATCH] Clear stale pending expedition lockouts Delete pending lockouts of members on expedition creation Delete pending lockouts when all members removed from expedition This fixes an edge case where members could incorrectly be assigned pending lockouts that were never cleared from the database (from a server crash or other situation) after entering another dz. --- zone/dynamiczone.cpp | 2 +- zone/dynamiczone.h | 2 +- zone/expedition.cpp | 6 ++++++ zone/expedition_database.cpp | 23 +++++++++++++++++++++++ zone/expedition_database.h | 1 + 5 files changed, 32 insertions(+), 2 deletions(-) diff --git a/zone/dynamiczone.cpp b/zone/dynamiczone.cpp index 754e7c31a..362f70140 100644 --- a/zone/dynamiczone.cpp +++ b/zone/dynamiczone.cpp @@ -427,7 +427,7 @@ void DynamicZone::RemoveAllCharacters(bool enable_removal_timers) database.RemoveClientsFromInstance(GetInstanceID()); } -void DynamicZone::SaveInstanceMembersToDatabase(const std::unordered_set character_ids) +void DynamicZone::SaveInstanceMembersToDatabase(const std::unordered_set& character_ids) { std::string insert_values; for (const auto& character_id : character_ids) diff --git a/zone/dynamiczone.h b/zone/dynamiczone.h index 54c58be9f..83063d207 100644 --- a/zone/dynamiczone.h +++ b/zone/dynamiczone.h @@ -75,7 +75,7 @@ public: uint32_t CreateInstance(); void AddCharacter(uint32_t character_id); - void SaveInstanceMembersToDatabase(const std::unordered_set character_ids); + void SaveInstanceMembersToDatabase(const std::unordered_set& character_ids); uint64_t GetExpireTime() const { return std::chrono::system_clock::to_time_t(m_expire_time); } uint16_t GetInstanceID() const { return static_cast(m_instance_id); }; diff --git a/zone/expedition.cpp b/zone/expedition.cpp index e6d46e34d..3dfb5403d 100644 --- a/zone/expedition.cpp +++ b/zone/expedition.cpp @@ -310,7 +310,9 @@ void Expedition::SaveMembers(ExpeditionRequest& request) { m_member_id_history.emplace(member.char_id); } + ExpeditionDatabase::InsertMembers(m_id, m_members); + ExpeditionDatabase::DeleteAllMembersPendingLockouts(m_members); m_dynamiczone.SaveInstanceMembersToDatabase(m_member_id_history); // all are current members here } @@ -504,10 +506,13 @@ void Expedition::RemoveAllMembers(bool enable_removal_timers) { m_dynamiczone.RemoveAllCharacters(enable_removal_timers); + ExpeditionDatabase::DeleteAllMembersPendingLockouts(m_members); ExpeditionDatabase::UpdateAllMembersRemoved(m_id); SendUpdatesToZoneMembers(true); SendWorldExpeditionUpdate(ServerOP_ExpeditionMembersRemoved); + + m_members.clear(); } bool Expedition::RemoveMember(const std::string& remove_char_name) @@ -1626,6 +1631,7 @@ void Expedition::HandleWorldMessage(ServerPacket* pack) if (expedition) { expedition->SendUpdatesToZoneMembers(true); + expedition->m_members.clear(); } } break; diff --git a/zone/expedition_database.cpp b/zone/expedition_database.cpp index 2e0816d97..2b9ddb658 100644 --- a/zone/expedition_database.cpp +++ b/zone/expedition_database.cpp @@ -379,6 +379,29 @@ void ExpeditionDatabase::DeletePendingLockouts(uint32_t character_id) database.QueryDatabase(query); } +void ExpeditionDatabase::DeleteAllMembersPendingLockouts(const std::vector& members) +{ + LogExpeditionsDetail("Deleting pending lockouts for [{}] characters", members.size()); + + std::string query_character_ids; + for (const auto& member : members) + { + fmt::format_to(std::back_inserter(query_character_ids), "{},", member.char_id); + } + + if (!query_character_ids.empty()) + { + query_character_ids.pop_back(); // trailing comma + + auto query = fmt::format(SQL( + DELETE FROM expedition_character_lockouts + WHERE character_id IN ({}) AND is_pending = TRUE; + ), query_character_ids); + + database.QueryDatabase(query); + } +} + void ExpeditionDatabase::DeleteLockout(uint32_t expedition_id, const std::string& event_name) { LogExpeditionsDetail("Deleting expedition [{}] lockout event [{}]", expedition_id, event_name); diff --git a/zone/expedition_database.h b/zone/expedition_database.h index 470840225..a267e8abd 100644 --- a/zone/expedition_database.h +++ b/zone/expedition_database.h @@ -55,6 +55,7 @@ namespace ExpeditionDatabase const std::vector& members, const std::string& expedition_name, const std::string& event_name); void AssignPendingLockouts(uint32_t character_id, const std::string& expedition_name); void DeletePendingLockouts(uint32_t character_id); + void DeleteAllMembersPendingLockouts(const std::vector& members); uint32_t GetExpeditionIDFromCharacterID(uint32_t character_id); uint32_t GetExpeditionIDFromInstanceID(uint32_t instance_id); ExpeditionMember GetExpeditionLeader(uint32_t expedition_id);