diff options
author | Shauren <shauren.trinity@gmail.com> | 2020-07-30 20:38:04 +0200 |
---|---|---|
committer | Shauren <shauren.trinity@gmail.com> | 2022-01-24 14:45:54 +0100 |
commit | a9b4f9aca0d0b90e59e0ed26e9bb4cce7d0ceeab (patch) | |
tree | c74e0a8e353302b085122869993ae0701a887d6d /src | |
parent | 54a6e603ffc8b4913669cf0f189a966d25b620d8 (diff) |
Core/Mail: Load mails at login instead of on demand when queried by packets (logging in always sends one of the packets that cause mail loading anyway)
(cherry picked from commit 57eaab80d9e1f6f25274f376da16e1f2f67ab4bc)
Diffstat (limited to 'src')
-rw-r--r-- | src/server/database/Database/Implementation/CharacterDatabase.cpp | 16 | ||||
-rw-r--r-- | src/server/database/Database/Implementation/CharacterDatabase.h | 2 | ||||
-rw-r--r-- | src/server/game/Entities/Player/Player.cpp | 73 | ||||
-rw-r--r-- | src/server/game/Entities/Player/Player.h | 15 | ||||
-rw-r--r-- | src/server/game/Globals/ObjectMgr.cpp | 17 | ||||
-rw-r--r-- | src/server/game/Handlers/CharacterHandler.cpp | 29 | ||||
-rw-r--r-- | src/server/game/Handlers/MailHandler.cpp | 8 | ||||
-rw-r--r-- | src/server/game/Mails/Mail.cpp | 56 |
8 files changed, 86 insertions, 130 deletions
diff --git a/src/server/database/Database/Implementation/CharacterDatabase.cpp b/src/server/database/Database/Implementation/CharacterDatabase.cpp index e7ccc8a3b90..6003983276b 100644 --- a/src/server/database/Database/Implementation/CharacterDatabase.cpp +++ b/src/server/database/Database/Implementation/CharacterDatabase.cpp @@ -121,8 +121,6 @@ void CharacterDatabaseConnection::DoPrepareStatements() PrepareStatement(CHAR_SEL_CHARACTER_REPUTATION, "SELECT faction, standing, flags FROM character_reputation WHERE guid = ?", CONNECTION_ASYNC); PrepareStatement(CHAR_SEL_CHARACTER_INVENTORY, "SELECT " SelectItemInstanceContent ", bag, slot FROM character_inventory ci JOIN item_instance ii ON ci.item = ii.guid LEFT JOIN item_instance_gems ig ON ii.guid = ig.itemGuid LEFT JOIN item_instance_transmog iit ON ii.guid = iit.itemGuid LEFT JOIN item_instance_modifiers im ON ii.guid = im.itemGuid WHERE ci.guid = ? ORDER BY (ii.flags & 0x80000) ASC, bag ASC, slot ASC", CONNECTION_ASYNC); PrepareStatement(CHAR_SEL_CHARACTER_ACTIONS, "SELECT a.button, a.action, a.type FROM character_action as a, characters as c WHERE a.guid = c.guid AND a.spec = c.activeTalentGroup AND a.guid = ? ORDER BY button", CONNECTION_ASYNC); - PrepareStatement(CHAR_SEL_CHARACTER_MAILCOUNT, "SELECT COUNT(id) FROM mail WHERE receiver = ? AND (checked & 1) = 0 AND deliver_time <= ?", CONNECTION_ASYNC); - PrepareStatement(CHAR_SEL_CHARACTER_MAILDATE, "SELECT MIN(deliver_time) FROM mail WHERE receiver = ? AND (checked & 1) = 0", CONNECTION_ASYNC); PrepareStatement(CHAR_SEL_MAIL_COUNT, "SELECT COUNT(*) FROM mail WHERE receiver = ?", CONNECTION_SYNCH); PrepareStatement(CHAR_SEL_CHARACTER_SOCIALLIST, "SELECT cs.friend, c.account, cs.flags, cs.note FROM character_social cs JOIN characters c ON c.guid = cs.friend WHERE cs.guid = ? AND c.deleteinfos_name IS NULL LIMIT 255", CONNECTION_ASYNC); PrepareStatement(CHAR_SEL_CHARACTER_HOMEBIND, "SELECT mapId, zoneId, posX, posY, posZ, orientation FROM character_homebind WHERE guid = ?", CONNECTION_ASYNC); @@ -155,17 +153,17 @@ void CharacterDatabaseConnection::DoPrepareStatements() PrepareStatement(CHAR_SEL_ACCOUNT_INSTANCELOCKTIMES, "SELECT instanceId, releaseTime FROM account_instance_times WHERE accountId = ?", CONNECTION_ASYNC); PrepareStatement(CHAR_SEL_CHARACTER_ACTIONS_SPEC, "SELECT button, action, type FROM character_action WHERE guid = ? AND spec = ? ORDER BY button", CONNECTION_ASYNC); - PrepareStatement(CHAR_SEL_MAILITEMS, "SELECT " SelectItemInstanceContent ", ii.owner_guid, m.id FROM mail_items mi INNER JOIN mail m ON mi.mail_id = m.id LEFT JOIN item_instance ii ON mi.item_guid = ii.guid LEFT JOIN item_instance_gems ig ON ii.guid = ig.itemGuid LEFT JOIN item_instance_transmog iit ON ii.guid = iit.itemGuid LEFT JOIN item_instance_modifiers im ON ii.guid = im.itemGuid WHERE m.receiver = ?", CONNECTION_SYNCH); - PrepareStatement(CHAR_SEL_MAILITEMS_ARTIFACT, "SELECT a.itemGuid, a.xp, a.artifactAppearanceId, a.artifactTierId, ap.artifactPowerId, ap.purchasedRank FROM item_instance_artifact_powers ap LEFT JOIN item_instance_artifact a ON ap.itemGuid = a.itemGuid INNER JOIN mail_items mi ON a.itemGuid = mi.item_guid INNER JOIN mail m ON mi.mail_id = m.id WHERE m.receiver = ?", CONNECTION_SYNCH); + PrepareStatement(CHAR_SEL_MAILITEMS, "SELECT " SelectItemInstanceContent ", ii.owner_guid, m.id FROM mail_items mi INNER JOIN mail m ON mi.mail_id = m.id LEFT JOIN item_instance ii ON mi.item_guid = ii.guid LEFT JOIN item_instance_gems ig ON ii.guid = ig.itemGuid LEFT JOIN item_instance_transmog iit ON ii.guid = iit.itemGuid LEFT JOIN item_instance_modifiers im ON ii.guid = im.itemGuid WHERE m.receiver = ?", CONNECTION_BOTH); + PrepareStatement(CHAR_SEL_MAILITEMS_ARTIFACT, "SELECT a.itemGuid, a.xp, a.artifactAppearanceId, a.artifactTierId, ap.artifactPowerId, ap.purchasedRank FROM item_instance_artifact_powers ap LEFT JOIN item_instance_artifact a ON ap.itemGuid = a.itemGuid INNER JOIN mail_items mi ON a.itemGuid = mi.item_guid INNER JOIN mail m ON mi.mail_id = m.id WHERE m.receiver = ?", CONNECTION_BOTH); PrepareStatement(CHAR_SEL_MAILITEMS_AZERITE, "SELECT iz.itemGuid, iz.xp, iz.level, iz.knowledgeLevel, " "iz.selectedAzeriteEssences1specId, iz.selectedAzeriteEssences1azeriteEssenceId1, iz.selectedAzeriteEssences1azeriteEssenceId2, iz.selectedAzeriteEssences1azeriteEssenceId3, iz.selectedAzeriteEssences1azeriteEssenceId4, " "iz.selectedAzeriteEssences2specId, iz.selectedAzeriteEssences2azeriteEssenceId1, iz.selectedAzeriteEssences2azeriteEssenceId2, iz.selectedAzeriteEssences2azeriteEssenceId3, iz.selectedAzeriteEssences2azeriteEssenceId4, " "iz.selectedAzeriteEssences3specId, iz.selectedAzeriteEssences3azeriteEssenceId1, iz.selectedAzeriteEssences3azeriteEssenceId2, iz.selectedAzeriteEssences3azeriteEssenceId3, iz.selectedAzeriteEssences3azeriteEssenceId4, " "iz.selectedAzeriteEssences4specId, iz.selectedAzeriteEssences4azeriteEssenceId1, iz.selectedAzeriteEssences4azeriteEssenceId2, iz.selectedAzeriteEssences4azeriteEssenceId3, iz.selectedAzeriteEssences4azeriteEssenceId4 " - "FROM item_instance_azerite iz INNER JOIN mail_items mi ON iz.itemGuid = mi.item_guid INNER JOIN mail m ON mi.mail_id = m.id WHERE m.receiver = ?", CONNECTION_SYNCH); - PrepareStatement(CHAR_SEL_MAILITEMS_AZERITE_MILESTONE_POWER, "SELECT iamp.itemGuid, iamp.azeriteItemMilestonePowerId FROM item_instance_azerite_milestone_power iamp INNER JOIN mail_items mi ON iamp.itemGuid = mi.item_guid INNER JOIN mail m ON mi.mail_id = m.id WHERE m.receiver = ?", CONNECTION_SYNCH); - PrepareStatement(CHAR_SEL_MAILITEMS_AZERITE_UNLOCKED_ESSENCE, "SELECT iaue.itemGuid, iaue.azeriteEssenceId, iaue.`rank` FROM item_instance_azerite_unlocked_essence iaue INNER JOIN mail_items mi ON iaue.itemGuid = mi.item_guid INNER JOIN mail m ON mi.mail_id = m.id WHERE m.receiver = ?", CONNECTION_SYNCH); - PrepareStatement(CHAR_SEL_MAILITEMS_AZERITE_EMPOWERED, "SELECT iae.itemGuid, iae.azeritePowerId1, iae.azeritePowerId2, iae.azeritePowerId3, iae.azeritePowerId4, iae.azeritePowerId5 FROM item_instance_azerite_empowered iae INNER JOIN mail_items mi ON iae.itemGuid = mi.item_guid INNER JOIN mail m ON mi.mail_id = m.id WHERE m.receiver = ?", CONNECTION_SYNCH); + "FROM item_instance_azerite iz INNER JOIN mail_items mi ON iz.itemGuid = mi.item_guid INNER JOIN mail m ON mi.mail_id = m.id WHERE m.receiver = ?", CONNECTION_BOTH); + PrepareStatement(CHAR_SEL_MAILITEMS_AZERITE_MILESTONE_POWER, "SELECT iamp.itemGuid, iamp.azeriteItemMilestonePowerId FROM item_instance_azerite_milestone_power iamp INNER JOIN mail_items mi ON iamp.itemGuid = mi.item_guid INNER JOIN mail m ON mi.mail_id = m.id WHERE m.receiver = ?", CONNECTION_BOTH); + PrepareStatement(CHAR_SEL_MAILITEMS_AZERITE_UNLOCKED_ESSENCE, "SELECT iaue.itemGuid, iaue.azeriteEssenceId, iaue.`rank` FROM item_instance_azerite_unlocked_essence iaue INNER JOIN mail_items mi ON iaue.itemGuid = mi.item_guid INNER JOIN mail m ON mi.mail_id = m.id WHERE m.receiver = ?", CONNECTION_BOTH); + PrepareStatement(CHAR_SEL_MAILITEMS_AZERITE_EMPOWERED, "SELECT iae.itemGuid, iae.azeritePowerId1, iae.azeritePowerId2, iae.azeritePowerId3, iae.azeritePowerId4, iae.azeritePowerId5 FROM item_instance_azerite_empowered iae INNER JOIN mail_items mi ON iae.itemGuid = mi.item_guid INNER JOIN mail m ON mi.mail_id = m.id WHERE m.receiver = ?", CONNECTION_BOTH); PrepareStatement(CHAR_SEL_AUCTION_ITEMS, "SELECT " SelectItemInstanceContent ", ii.owner_guid, ai.auctionId FROM auction_items ai INNER JOIN item_instance ii ON ai.itemGuid = ii.guid LEFT JOIN item_instance_gems ig ON ii.guid = ig.itemGuid LEFT JOIN item_instance_transmog iit ON ii.guid = iit.itemGuid LEFT JOIN item_instance_modifiers im ON ii.guid = im.itemGuid", CONNECTION_SYNCH); PrepareStatement(CHAR_SEL_AUCTIONS, "SELECT id, auctionHouseId, owner, bidder, minBid, buyoutOrUnitPrice, deposit, bidAmount, startTime, endTime FROM auctionhouse", CONNECTION_SYNCH); PrepareStatement(CHAR_INS_AUCTION_ITEMS, "INSERT INTO auction_items (auctionId, itemGuid) VALUES (?, ?)", CONNECTION_ASYNC); @@ -556,7 +554,7 @@ void CharacterDatabaseConnection::DoPrepareStatements() PrepareStatement(CHAR_SEL_CHAR_COD_ITEM_MAIL, "SELECT id, messageType, mailTemplateId, sender, subject, body, money, has_items FROM mail WHERE receiver = ? AND has_items <> 0 AND cod <> 0", CONNECTION_SYNCH); PrepareStatement(CHAR_SEL_CHAR_SOCIAL, "SELECT DISTINCT guid FROM character_social WHERE friend = ?", CONNECTION_SYNCH); PrepareStatement(CHAR_SEL_CHAR_OLD_CHARS, "SELECT guid, deleteInfos_Account FROM characters WHERE deleteDate IS NOT NULL AND deleteDate < ?", CONNECTION_SYNCH); - PrepareStatement(CHAR_SEL_MAIL, "SELECT id, messageType, sender, receiver, subject, body, expire_time, deliver_time, money, cod, checked, stationery, mailTemplateId FROM mail WHERE receiver = ? ORDER BY id DESC", CONNECTION_SYNCH); + PrepareStatement(CHAR_SEL_MAIL, "SELECT id, messageType, sender, receiver, subject, body, expire_time, deliver_time, money, cod, checked, stationery, mailTemplateId FROM mail WHERE receiver = ? ORDER BY id DESC", CONNECTION_ASYNC); PrepareStatement(CHAR_DEL_CHAR_AURA_FROZEN, "DELETE FROM character_aura WHERE spell = 9454 AND guid = ?", CONNECTION_ASYNC); PrepareStatement(CHAR_SEL_CHAR_INVENTORY_COUNT_ITEM, "SELECT COUNT(itemEntry) FROM character_inventory ci INNER JOIN item_instance ii ON ii.guid = ci.item WHERE itemEntry = ?", CONNECTION_SYNCH); PrepareStatement(CHAR_SEL_MAIL_COUNT_ITEM, "SELECT COUNT(itemEntry) FROM mail_items mi INNER JOIN item_instance ii ON ii.guid = mi.item_guid WHERE itemEntry = ?", CONNECTION_SYNCH); diff --git a/src/server/database/Database/Implementation/CharacterDatabase.h b/src/server/database/Database/Implementation/CharacterDatabase.h index 5073458f399..b83ed38531d 100644 --- a/src/server/database/Database/Implementation/CharacterDatabase.h +++ b/src/server/database/Database/Implementation/CharacterDatabase.h @@ -94,8 +94,6 @@ enum CharacterDatabaseStatements : uint32 CHAR_SEL_CHARACTER_INVENTORY, CHAR_SEL_CHARACTER_ACTIONS, CHAR_SEL_CHARACTER_ACTIONS_SPEC, - CHAR_SEL_CHARACTER_MAILCOUNT, - CHAR_SEL_CHARACTER_MAILDATE, CHAR_SEL_MAIL_COUNT, CHAR_SEL_CHARACTER_SOCIALLIST, CHAR_SEL_CHARACTER_HOMEBIND, diff --git a/src/server/game/Entities/Player/Player.cpp b/src/server/game/Entities/Player/Player.cpp index f3798736082..b33e9b61cd1 100644 --- a/src/server/game/Entities/Player/Player.cpp +++ b/src/server/game/Entities/Player/Player.cpp @@ -247,7 +247,6 @@ Player::Player(WorldSession* session) : Unit(true), m_sceneMgr(this) m_oldpetspell = 0; m_lastpetnumber = 0; - m_mailsLoaded = false; m_mailsUpdated = false; unReadMails = 0; m_nextMailDelivereTime = 0; @@ -18525,7 +18524,13 @@ bool Player::LoadFromDB(ObjectGuid guid, CharacterDatabaseQueryHolder* holder) _LoadActions(holder->GetPreparedResult(PLAYER_LOGIN_QUERY_LOAD_ACTIONS)); // unread mails and next delivery time, actual mails not loaded - _LoadMailInit(holder->GetPreparedResult(PLAYER_LOGIN_QUERY_LOAD_MAIL_COUNT), holder->GetPreparedResult(PLAYER_LOGIN_QUERY_LOAD_MAIL_DATE)); + _LoadMail(holder->GetPreparedResult(PLAYER_LOGIN_QUERY_LOAD_MAILS), + holder->GetPreparedResult(PLAYER_LOGIN_QUERY_LOAD_MAIL_ITEMS), + holder->GetPreparedResult(PLAYER_LOGIN_QUERY_LOAD_MAIL_ITEMS_ARTIFACT), + holder->GetPreparedResult(PLAYER_LOGIN_QUERY_LOAD_MAIL_ITEMS_AZERITE), + holder->GetPreparedResult(PLAYER_LOGIN_QUERY_LOAD_MAIL_ITEMS_AZERITE_MILESTONE_POWER), + holder->GetPreparedResult(PLAYER_LOGIN_QUERY_LOAD_MAIL_ITEMS_AZERITE_UNLOCKED_ESSENCE), + holder->GetPreparedResult(PLAYER_LOGIN_QUERY_LOAD_MAIL_ITEMS_AZERITE_EMPOWERED)); m_social = sSocialMgr->LoadFromDB(holder->GetPreparedResult(PLAYER_LOGIN_QUERY_LOAD_SOCIAL_LIST), GetGUID()); @@ -19399,34 +19404,18 @@ Item* Player::_LoadMailedItem(ObjectGuid const& playerGuid, Player* player, uint return item; } -void Player::_LoadMailInit(PreparedQueryResult resultUnread, PreparedQueryResult resultDelivery) -{ - //set a count of unread mails - //QueryResult* resultMails = CharacterDatabase.PQuery("SELECT COUNT(id) FROM mail WHERE receiver = '%u' AND (checked & 1)=0 AND deliver_time <= '" UI64FMTD "'", GUID_LOPART(playerGuid), (uint64)cTime); - if (resultUnread) - unReadMails = uint8((*resultUnread)[0].GetUInt64()); - - // store nearest delivery time (it > 0 and if it < current then at next player update SendNewMaill will be called) - //resultMails = CharacterDatabase.PQuery("SELECT MIN(deliver_time) FROM mail WHERE receiver = '%u' AND (checked & 1)=0", GUID_LOPART(playerGuid)); - if (resultDelivery) - m_nextMailDelivereTime = time_t((*resultDelivery)[0].GetUInt32()); -} - -void Player::_LoadMail() +void Player::_LoadMail(PreparedQueryResult mailsResult, PreparedQueryResult mailItemsResult, PreparedQueryResult artifactResult, PreparedQueryResult azeriteItemResult, + PreparedQueryResult azeriteItemMilestonePowersResult, PreparedQueryResult azeriteItemUnlockedEssencesResult, PreparedQueryResult azeriteEmpoweredItemResult) { m_mail.clear(); - CharacterDatabasePreparedStatement* stmt = CharacterDatabase.GetPreparedStatement(CHAR_SEL_MAIL); - stmt->setUInt64(0, GetGUID().GetCounter()); - PreparedQueryResult result = CharacterDatabase.Query(stmt); - std::unordered_map<uint32, Mail*> mailById; - if (result) + if (mailsResult) { do { - Field* fields = result->Fetch(); + Field* fields = mailsResult->Fetch(); Mail* m = new Mail(); m->messageID = fields[0].GetUInt32(); @@ -19454,49 +19443,24 @@ void Player::_LoadMail() m_mail.push_back(m); mailById[m->messageID] = m; } - while (result->NextRow()); + while (mailsResult->NextRow()); } - stmt = CharacterDatabase.GetPreparedStatement(CHAR_SEL_MAILITEMS); - stmt->setUInt64(0, GetGUID().GetCounter()); - result = CharacterDatabase.Query(stmt); - - if (result) + if (mailItemsResult) { - stmt = CharacterDatabase.GetPreparedStatement(CHAR_SEL_MAILITEMS_ARTIFACT); - stmt->setUInt64(0, GetGUID().GetCounter()); - PreparedQueryResult artifactResult = CharacterDatabase.Query(stmt); - - stmt = CharacterDatabase.GetPreparedStatement(CHAR_SEL_MAILITEMS_AZERITE); - stmt->setUInt64(0, GetGUID().GetCounter()); - PreparedQueryResult azeriteResult = CharacterDatabase.Query(stmt); - - stmt = CharacterDatabase.GetPreparedStatement(CHAR_SEL_MAILITEMS_AZERITE_MILESTONE_POWER); - stmt->setUInt64(0, GetGUID().GetCounter()); - PreparedQueryResult azeriteItemMilestonePowersResult = CharacterDatabase.Query(stmt); - - stmt = CharacterDatabase.GetPreparedStatement(CHAR_SEL_MAILITEMS_AZERITE_UNLOCKED_ESSENCE); - stmt->setUInt64(0, GetGUID().GetCounter()); - PreparedQueryResult azeriteItemUnlockedEssencesResult = CharacterDatabase.Query(stmt); - - stmt = CharacterDatabase.GetPreparedStatement(CHAR_SEL_MAILITEMS_AZERITE_EMPOWERED); - stmt->setUInt64(0, GetGUID().GetCounter()); - PreparedQueryResult azeriteEmpoweredItemResult = CharacterDatabase.Query(stmt); - std::unordered_map<ObjectGuid::LowType, ItemAdditionalLoadInfo> additionalData; - ItemAdditionalLoadInfo::Init(&additionalData, artifactResult, azeriteResult, azeriteItemMilestonePowersResult, + ItemAdditionalLoadInfo::Init(&additionalData, artifactResult, azeriteItemResult, azeriteItemMilestonePowersResult, azeriteItemUnlockedEssencesResult, azeriteEmpoweredItemResult); do { - Field* fields = result->Fetch(); + Field* fields = mailItemsResult->Fetch(); uint32 mailId = fields[52].GetUInt32(); _LoadMailedItem(GetGUID(), this, mailId, mailById[mailId], fields, Trinity::Containers::MapGetValuePtr(additionalData, fields[0].GetUInt64())); - } - while (result->NextRow()); + } while (mailItemsResult->NextRow()); } - m_mailsLoaded = true; + UpdateNextMailTimeAndUnreads(); } void Player::LoadPet() @@ -21190,9 +21154,6 @@ void Player::_SaveCUFProfiles(CharacterDatabaseTransaction& trans) void Player::_SaveMail(CharacterDatabaseTransaction& trans) { - if (!m_mailsLoaded) - return; - CharacterDatabasePreparedStatement* stmt; for (PlayerMails::iterator itr = m_mail.begin(); itr != m_mail.end(); ++itr) diff --git a/src/server/game/Entities/Player/Player.h b/src/server/game/Entities/Player/Player.h index 965fbe7d00a..26e013d2b63 100644 --- a/src/server/game/Entities/Player/Player.h +++ b/src/server/game/Entities/Player/Player.h @@ -854,8 +854,13 @@ enum PlayerLoginQueryIndex PLAYER_LOGIN_QUERY_LOAD_AZERITE_UNLOCKED_ESSENCES, PLAYER_LOGIN_QUERY_LOAD_AZERITE_EMPOWERED, PLAYER_LOGIN_QUERY_LOAD_ACTIONS, - PLAYER_LOGIN_QUERY_LOAD_MAIL_COUNT, - PLAYER_LOGIN_QUERY_LOAD_MAIL_DATE, + PLAYER_LOGIN_QUERY_LOAD_MAILS, + PLAYER_LOGIN_QUERY_LOAD_MAIL_ITEMS, + PLAYER_LOGIN_QUERY_LOAD_MAIL_ITEMS_ARTIFACT, + PLAYER_LOGIN_QUERY_LOAD_MAIL_ITEMS_AZERITE, + PLAYER_LOGIN_QUERY_LOAD_MAIL_ITEMS_AZERITE_MILESTONE_POWER, + PLAYER_LOGIN_QUERY_LOAD_MAIL_ITEMS_AZERITE_UNLOCKED_ESSENCE, + PLAYER_LOGIN_QUERY_LOAD_MAIL_ITEMS_AZERITE_EMPOWERED, PLAYER_LOGIN_QUERY_LOAD_SOCIAL_LIST, PLAYER_LOGIN_QUERY_LOAD_HOME_BIND, PLAYER_LOGIN_QUERY_LOAD_SPELL_COOLDOWNS, @@ -1684,7 +1689,6 @@ class TC_GAME_API Player : public Unit, public GridObject<Player> static void DeleteOldCharacters(); static void DeleteOldCharacters(uint32 keepDays); - bool m_mailsLoaded; bool m_mailsUpdated; void SetBindPoint(ObjectGuid guid) const; @@ -1717,7 +1721,6 @@ class TC_GAME_API Player : public Unit, public GridObject<Player> void SendNewMail() const; void UpdateNextMailTimeAndUnreads(); void AddNewMailDeliverTime(time_t deliver_time); - bool IsMailsLoaded() const { return m_mailsLoaded; } void RemoveMail(uint32 id); @@ -2804,8 +2807,8 @@ class TC_GAME_API Player : public Unit, public GridObject<Player> PreparedQueryResult azeriteItemMilestonePowersResult, PreparedQueryResult azeriteItemUnlockedEssencesResult, PreparedQueryResult azeriteEmpoweredItemResult, uint32 timeDiff); void _LoadVoidStorage(PreparedQueryResult result); - void _LoadMailInit(PreparedQueryResult resultUnread, PreparedQueryResult resultDelivery); - void _LoadMail(); + void _LoadMail(PreparedQueryResult mailsResult, PreparedQueryResult mailItemsResult, PreparedQueryResult artifactResult, PreparedQueryResult azeriteItemResult, + PreparedQueryResult azeriteItemMilestonePowersResult, PreparedQueryResult azeriteItemUnlockedEssencesResult, PreparedQueryResult azeriteEmpoweredItemResult); static Item* _LoadMailedItem(ObjectGuid const& playerGuid, Player* player, uint32 mailId, Mail* mail, Field* fields, ItemAdditionalLoadInfo* addionalData); void _LoadQuestStatus(PreparedQueryResult result); void _LoadQuestStatusObjectives(PreparedQueryResult result); diff --git a/src/server/game/Globals/ObjectMgr.cpp b/src/server/game/Globals/ObjectMgr.cpp index 62ae41babdd..a82aae71be1 100644 --- a/src/server/game/Globals/ObjectMgr.cpp +++ b/src/server/game/Globals/ObjectMgr.cpp @@ -6409,11 +6409,15 @@ void ObjectMgr::ReturnOrDeleteOldMails(bool serverUp) do { Field* fields = result->Fetch(); + ObjectGuid::LowType receiver = fields[3].GetUInt64(); + if (serverUp && ObjectAccessor::FindConnectedPlayer(ObjectGuid::Create<HighGuid::Player>(receiver))) + continue; + Mail* m = new Mail; m->messageID = fields[0].GetUInt32(); m->messageType = fields[1].GetUInt8(); m->sender = fields[2].GetUInt64(); - m->receiver = fields[3].GetUInt64(); + m->receiver = receiver; bool has_items = fields[4].GetBool(); m->expire_time = fields[5].GetInt64(); m->deliver_time = 0; @@ -6421,17 +6425,6 @@ void ObjectMgr::ReturnOrDeleteOldMails(bool serverUp) m->checked = fields[7].GetUInt8(); m->mailTemplateId = fields[8].GetInt16(); - Player* player = nullptr; - if (serverUp) - player = ObjectAccessor::FindConnectedPlayer(ObjectGuid::Create<HighGuid::Player>(m->receiver)); - - if (player && player->m_mailsLoaded) - { // this code will run very improbably (the time is between 4 and 5 am, in game is online a player, who has old mail - // his in mailbox and he has already listed his mails) - delete m; - continue; - } - // Delete or return mail if (has_items) { diff --git a/src/server/game/Handlers/CharacterHandler.cpp b/src/server/game/Handlers/CharacterHandler.cpp index b1359f1f064..ef67ac1b114 100644 --- a/src/server/game/Handlers/CharacterHandler.cpp +++ b/src/server/game/Handlers/CharacterHandler.cpp @@ -183,14 +183,33 @@ bool LoginQueryHolder::Initialize() stmt->setUInt64(0, lowGuid); res &= SetPreparedQuery(PLAYER_LOGIN_QUERY_LOAD_ACTIONS, stmt); - stmt = CharacterDatabase.GetPreparedStatement(CHAR_SEL_CHARACTER_MAILCOUNT); + stmt = CharacterDatabase.GetPreparedStatement(CHAR_SEL_MAIL); stmt->setUInt64(0, lowGuid); - stmt->setUInt64(1, GameTime::GetGameTime()); - res &= SetPreparedQuery(PLAYER_LOGIN_QUERY_LOAD_MAIL_COUNT, stmt); + res &= SetPreparedQuery(PLAYER_LOGIN_QUERY_LOAD_MAILS, stmt); - stmt = CharacterDatabase.GetPreparedStatement(CHAR_SEL_CHARACTER_MAILDATE); + stmt = CharacterDatabase.GetPreparedStatement(CHAR_SEL_MAILITEMS); stmt->setUInt64(0, lowGuid); - res &= SetPreparedQuery(PLAYER_LOGIN_QUERY_LOAD_MAIL_DATE, stmt); + res &= SetPreparedQuery(PLAYER_LOGIN_QUERY_LOAD_MAIL_ITEMS, stmt); + + stmt = CharacterDatabase.GetPreparedStatement(CHAR_SEL_MAILITEMS_ARTIFACT); + stmt->setUInt64(0, lowGuid); + res &= SetPreparedQuery(PLAYER_LOGIN_QUERY_LOAD_MAIL_ITEMS_ARTIFACT, stmt); + + stmt = CharacterDatabase.GetPreparedStatement(CHAR_SEL_MAILITEMS_AZERITE); + stmt->setUInt64(0, lowGuid); + res &= SetPreparedQuery(PLAYER_LOGIN_QUERY_LOAD_MAIL_ITEMS_AZERITE, stmt); + + stmt = CharacterDatabase.GetPreparedStatement(CHAR_SEL_MAILITEMS_AZERITE_MILESTONE_POWER); + stmt->setUInt64(0, lowGuid); + res &= SetPreparedQuery(PLAYER_LOGIN_QUERY_LOAD_MAIL_ITEMS_AZERITE_MILESTONE_POWER, stmt); + + stmt = CharacterDatabase.GetPreparedStatement(CHAR_SEL_MAILITEMS_AZERITE_UNLOCKED_ESSENCE); + stmt->setUInt64(0, lowGuid); + res &= SetPreparedQuery(PLAYER_LOGIN_QUERY_LOAD_MAIL_ITEMS_AZERITE_UNLOCKED_ESSENCE, stmt); + + stmt = CharacterDatabase.GetPreparedStatement(CHAR_SEL_MAILITEMS_AZERITE_EMPOWERED); + stmt->setUInt64(0, lowGuid); + res &= SetPreparedQuery(PLAYER_LOGIN_QUERY_LOAD_MAIL_ITEMS_AZERITE_EMPOWERED, stmt); stmt = CharacterDatabase.GetPreparedStatement(CHAR_SEL_CHARACTER_SOCIALLIST); stmt->setUInt64(0, lowGuid); diff --git a/src/server/game/Handlers/MailHandler.cpp b/src/server/game/Handlers/MailHandler.cpp index f2c9a767dba..f2b4f4a79f4 100644 --- a/src/server/game/Handlers/MailHandler.cpp +++ b/src/server/game/Handlers/MailHandler.cpp @@ -572,10 +572,6 @@ void WorldSession::HandleGetMailList(WorldPackets::Mail::MailGetList& packet) Player* player = _player; - //load players mails, and mailed items - if (!player->m_mailsLoaded) - player->_LoadMail(); - WorldPackets::Mail::MailListResult response; time_t curTime = GameTime::GetGameTime(); @@ -655,14 +651,10 @@ void WorldSession::HandleMailCreateTextItem(WorldPackets::Mail::MailCreateTextIt } } -/// @todo Fix me! ... this void has probably bad condition, but good data are sent void WorldSession::HandleQueryNextMailTime(WorldPackets::Mail::MailQueryNextMailTime& /*packet*/) { WorldPackets::Mail::MailQueryNextTimeResult result; - if (!_player->m_mailsLoaded) - _player->_LoadMail(); - if (_player->unReadMails > 0) { result.NextMailTime = 0.0f; diff --git a/src/server/game/Mails/Mail.cpp b/src/server/game/Mails/Mail.cpp index c9ad975540b..731607645ae 100644 --- a/src/server/game/Mails/Mail.cpp +++ b/src/server/game/Mails/Mail.cpp @@ -252,43 +252,35 @@ void MailDraft::SendMailTo(CharacterDatabaseTransaction& trans, MailReceiver con { pReceiver->AddNewMailDeliverTime(deliver_time); - if (pReceiver->IsMailsLoaded()) + Mail* m = new Mail; + m->messageID = mailId; + m->mailTemplateId = GetMailTemplateId(); + m->subject = GetSubject(); + m->body = GetBody(); + m->money = GetMoney(); + m->COD = GetCOD(); + + for (MailItemMap::const_iterator mailItemIter = m_items.begin(); mailItemIter != m_items.end(); ++mailItemIter) { - Mail* m = new Mail; - m->messageID = mailId; - m->mailTemplateId = GetMailTemplateId(); - m->subject = GetSubject(); - m->body = GetBody(); - m->money = GetMoney(); - m->COD = GetCOD(); - - for (MailItemMap::const_iterator mailItemIter = m_items.begin(); mailItemIter != m_items.end(); ++mailItemIter) - { - Item* item = mailItemIter->second; - m->AddItem(item->GetGUID().GetCounter(), item->GetEntry()); - } + Item* item = mailItemIter->second; + m->AddItem(item->GetGUID().GetCounter(), item->GetEntry()); + } - m->messageType = sender.GetMailMessageType(); - m->stationery = sender.GetStationery(); - m->sender = sender.GetSenderId(); - m->receiver = receiver.GetPlayerGUIDLow(); - m->expire_time = expire_time; - m->deliver_time = deliver_time; - m->checked = checked; - m->state = MAIL_STATE_UNCHANGED; + m->messageType = sender.GetMailMessageType(); + m->stationery = sender.GetStationery(); + m->sender = sender.GetSenderId(); + m->receiver = receiver.GetPlayerGUIDLow(); + m->expire_time = expire_time; + m->deliver_time = deliver_time; + m->checked = checked; + m->state = MAIL_STATE_UNCHANGED; - pReceiver->AddMail(m); // to insert new mail to beginning of maillist + pReceiver->AddMail(m); // to insert new mail to beginning of maillist - if (!m_items.empty()) - { - for (MailItemMap::iterator mailItemIter = m_items.begin(); mailItemIter != m_items.end(); ++mailItemIter) - pReceiver->AddMItem(mailItemIter->second); - } - } - else if (!m_items.empty()) + if (!m_items.empty()) { - CharacterDatabaseTransaction temp = CharacterDatabaseTransaction(nullptr); - deleteIncludedItems(temp); + for (MailItemMap::iterator mailItemIter = m_items.begin(); mailItemIter != m_items.end(); ++mailItemIter) + pReceiver->AddMItem(mailItemIter->second); } } else if (!m_items.empty()) |