diff options
author | Treeston <treeston.mmoc@gmail.com> | 2019-08-01 23:41:45 +0200 |
---|---|---|
committer | Treeston <treeston.mmoc@gmail.com> | 2019-08-01 23:42:14 +0200 |
commit | fedf1f557b2aa1cbb0f4bc722b24afb59cc30855 (patch) | |
tree | 257906ea9908c1f154cc943bbd20a31e959e2e99 /src | |
parent | 22c5419bf266790801cbeb62a619b2331be064ed (diff) |
Core/Chat: Custom channel preservation rewrite. Channel data is now loaded at startup, and written to the DB periodically, instead of both things happening in real time.
Diffstat (limited to 'src')
-rw-r--r-- | src/server/database/Database/Implementation/CharacterDatabase.cpp | 6 | ||||
-rw-r--r-- | src/server/database/Database/Implementation/CharacterDatabase.h | 3 | ||||
-rw-r--r-- | src/server/game/Chat/Channels/Channel.cpp | 75 | ||||
-rw-r--r-- | src/server/game/Chat/Channels/Channel.h | 18 | ||||
-rw-r--r-- | src/server/game/Chat/Channels/ChannelMgr.cpp | 113 | ||||
-rw-r--r-- | src/server/game/Chat/Channels/ChannelMgr.h | 4 | ||||
-rw-r--r-- | src/server/game/Entities/Player/Player.cpp | 2 | ||||
-rw-r--r-- | src/server/game/World/World.cpp | 23 | ||||
-rw-r--r-- | src/server/game/World/World.h | 2 | ||||
-rw-r--r-- | src/server/worldserver/worldserver.conf.dist | 7 |
10 files changed, 162 insertions, 91 deletions
diff --git a/src/server/database/Database/Implementation/CharacterDatabase.cpp b/src/server/database/Database/Implementation/CharacterDatabase.cpp index c7eab8ba321..e924eb907a3 100644 --- a/src/server/database/Database/Implementation/CharacterDatabase.cpp +++ b/src/server/database/Database/Implementation/CharacterDatabase.cpp @@ -226,11 +226,11 @@ void CharacterDatabaseConnection::DoPrepareStatements() PrepareStatement(CHAR_SEL_CHAR_DATA_FOR_GUILD, "SELECT name, level, class, gender, zone, account FROM characters WHERE guid = ?", CONNECTION_SYNCH); // Chat channel handling - PrepareStatement(CHAR_SEL_CHANNEL, "SELECT name, announce, ownership, password, bannedList FROM channels WHERE name = ? AND team = ?", CONNECTION_SYNCH); - PrepareStatement(CHAR_INS_CHANNEL, "INSERT INTO channels(name, team, lastUsed) VALUES (?, ?, UNIX_TIMESTAMP())", CONNECTION_ASYNC); - PrepareStatement(CHAR_UPD_CHANNEL, "UPDATE channels SET announce = ?, ownership = ?, password = ?, bannedList = ?, lastUsed = UNIX_TIMESTAMP() WHERE name = ? AND team = ?", CONNECTION_ASYNC); + PrepareStatement(CHAR_UPD_CHANNEL, "INSERT INTO channels (name, team, announce, ownership, password, bannedList, lastUsed) VALUES (?, ?, ?, ?, ?, ?, UNIX_TIMESTAMP()) " + "ON DUPLICATE KEY UPDATE announce=VALUES(announce), ownership=VALUES(ownership), password=VALUES(password), bannedList=VALUES(bannedList), lastUsed=VALUES(lastUsed)", CONNECTION_ASYNC); PrepareStatement(CHAR_UPD_CHANNEL_USAGE, "UPDATE channels SET lastUsed = UNIX_TIMESTAMP() WHERE name = ? AND team = ?", CONNECTION_ASYNC); PrepareStatement(CHAR_UPD_CHANNEL_OWNERSHIP, "UPDATE channels SET ownership = ? WHERE name LIKE ?", CONNECTION_ASYNC); + PrepareStatement(CHAR_DEL_CHANNEL, "DELETE FROM channels WHERE name = ? AND team = ?", CONNECTION_ASYNC); PrepareStatement(CHAR_DEL_OLD_CHANNELS, "DELETE FROM channels WHERE ownership = 1 AND lastUsed + ? < UNIX_TIMESTAMP()", CONNECTION_ASYNC); // Equipmentsets diff --git a/src/server/database/Database/Implementation/CharacterDatabase.h b/src/server/database/Database/Implementation/CharacterDatabase.h index 2397b620a06..1936708a17d 100644 --- a/src/server/database/Database/Implementation/CharacterDatabase.h +++ b/src/server/database/Database/Implementation/CharacterDatabase.h @@ -191,11 +191,10 @@ enum CharacterDatabaseStatements : uint32 CHAR_DEL_GUILD_MEMBER_WITHDRAW, CHAR_SEL_CHAR_DATA_FOR_GUILD, - CHAR_SEL_CHANNEL, - CHAR_INS_CHANNEL, CHAR_UPD_CHANNEL, CHAR_UPD_CHANNEL_USAGE, CHAR_UPD_CHANNEL_OWNERSHIP, + CHAR_DEL_CHANNEL, CHAR_DEL_OLD_CHANNELS, CHAR_UPD_EQUIP_SET, diff --git a/src/server/game/Chat/Channels/Channel.cpp b/src/server/game/Chat/Channels/Channel.cpp index d9fa3fc054b..d0e31732006 100644 --- a/src/server/game/Chat/Channels/Channel.cpp +++ b/src/server/game/Chat/Channels/Channel.cpp @@ -22,6 +22,7 @@ #include "Chat.h" #include "DatabaseEnv.h" #include "DBCStores.h" +#include "GameTime.h" #include "GridNotifiers.h" #include "GridNotifiersImpl.h" #include "Language.h" @@ -33,9 +34,10 @@ #include "World.h" Channel::Channel(uint32 channelId, uint32 team /*= 0*/, AreaTableEntry const* zoneEntry /*= nullptr*/) : + _isDirty(false), + _nextActivityUpdateTime(0), _announceEnabled(false), // no join/leave announces _ownershipEnabled(false), // no ownership handout - _persistentChannel(false), _isOwnerInvisible(false), _channelFlags(CHANNEL_FLAG_GENERAL), // for all built-in channels _channelId(channelId), @@ -59,9 +61,10 @@ Channel::Channel(uint32 channelId, uint32 team /*= 0*/, AreaTableEntry const* zo } Channel::Channel(std::string const& name, uint32 team /*= 0*/, std::string const& banList) : + _isDirty(false), + _nextActivityUpdateTime(0), _announceEnabled(true), _ownershipEnabled(true), - _persistentChannel(sWorld->getBoolConfig(CONFIG_PRESERVE_CUSTOM_CHANNELS)), _isOwnerInvisible(false), _channelFlags(CHANNEL_FLAG_CUSTOM), _channelId(0), @@ -108,9 +111,10 @@ std::string Channel::GetName(LocaleConstant locale /*= DEFAULT_LOCALE*/) const return result; } -void Channel::UpdateChannelInDB() const +void Channel::UpdateChannelInDB() { - if (_persistentChannel) + time_t const now = GameTime::GetGameTime(); + if (_isDirty) { std::ostringstream banlist; for (BannedContainer::const_iterator iter = _bannedStore.begin(); iter != _bannedStore.end(); ++iter) @@ -119,36 +123,29 @@ void Channel::UpdateChannelInDB() const std::string banListStr = banlist.str(); PreparedStatement* stmt = CharacterDatabase.GetPreparedStatement(CHAR_UPD_CHANNEL); - stmt->setBool(0, _announceEnabled); - stmt->setBool(1, _ownershipEnabled); - stmt->setString(2, _channelPassword); - stmt->setString(3, banListStr); - stmt->setString(4, _channelName); - stmt->setUInt32(5, _channelTeam); + stmt->setString(0, _channelName); + stmt->setUInt32(1, _channelTeam); + stmt->setBool(2, _announceEnabled); + stmt->setBool(3, _ownershipEnabled); + stmt->setString(4, _channelPassword); + stmt->setString(5, banListStr); CharacterDatabase.Execute(stmt); - - TC_LOG_DEBUG("chat.system", "Channel(%s) updated in database", _channelName.c_str()); } -} - -void Channel::UpdateChannelUseageInDB() const -{ - PreparedStatement* stmt = CharacterDatabase.GetPreparedStatement(CHAR_UPD_CHANNEL_USAGE); - stmt->setString(0, _channelName); - stmt->setUInt32(1, _channelTeam); - CharacterDatabase.Execute(stmt); -} - -void Channel::CleanOldChannelsInDB() -{ - if (sWorld->getIntConfig(CONFIG_PRESERVE_CUSTOM_CHANNEL_DURATION) > 0) + else if (_nextActivityUpdateTime <= now) { - PreparedStatement* stmt = CharacterDatabase.GetPreparedStatement(CHAR_DEL_OLD_CHANNELS); - stmt->setUInt32(0, sWorld->getIntConfig(CONFIG_PRESERVE_CUSTOM_CHANNEL_DURATION) * DAY); - CharacterDatabase.Execute(stmt); - - TC_LOG_DEBUG("chat.system", "Cleaned out unused custom chat channels."); + if (!_playersStore.empty()) + { + PreparedStatement* stmt = CharacterDatabase.GetPreparedStatement(CHAR_UPD_CHANNEL_USAGE); + stmt->setString(0, _channelName); + stmt->setUInt32(1, _channelTeam); + CharacterDatabase.Execute(stmt); + } } + else + return; + + _isDirty = false; + _nextActivityUpdateTime = now + urand(1 * MINUTE, 6 * MINUTE) * std::max(1u, sWorld->getIntConfig(CONFIG_PRESERVE_CUSTOM_CHANNEL_INTERVAL)); } void Channel::JoinChannel(Player* player, std::string const& pass) @@ -203,6 +200,8 @@ void Channel::JoinChannel(Player* player, std::string const& pass) } bool newChannel = _playersStore.empty(); + if (newChannel) + _nextActivityUpdateTime = 0; // force activity update on next channel tick PlayerInfo& pinfo = _playersStore[guid]; pinfo.flags = MEMBER_FLAG_NONE; @@ -217,9 +216,6 @@ void Channel::JoinChannel(Player* player, std::string const& pass) // Custom channel handling if (!IsConstant()) { - // Update last_used timestamp in db - UpdateChannelUseageInDB(); - // If the channel has no owner yet and ownership is allowed, set the new owner. // or if the owner was a GM with .gm visible off // don't do this if the new player is, too, an invis GM, unless the channel was empty @@ -271,9 +267,6 @@ void Channel::LeaveChannel(Player* player, bool send) if (!IsConstant()) { - // Update last_used timestamp in db - UpdateChannelUseageInDB(); - // If the channel owner left and there are players still inside, pick a new owner // do not pick invisible gm owner unless there are only invisible gms in that channel (rare) if (changeowner && _ownershipEnabled && !_playersStore.empty()) @@ -344,7 +337,7 @@ void Channel::KickOrBan(Player const* player, std::string const& badname, bool b if (ban && !IsBanned(victim)) { _bannedStore.insert(victim); - UpdateChannelInDB(); + _isDirty = true; if (!player->GetSession()->HasPermission(rbac::RBAC_PERM_SILENTLY_JOIN_CHANNEL)) { @@ -409,7 +402,7 @@ void Channel::UnBan(Player const* player, std::string const& badname) ChannelNameBuilder<PlayerUnbannedAppend> builder(this, appender); SendToAll(builder); - UpdateChannelInDB(); + _isDirty = true; } void Channel::Password(Player const* player, std::string const& pass) @@ -440,7 +433,7 @@ void Channel::Password(Player const* player, std::string const& pass) ChannelNameBuilder<PasswordChangedAppend> builder(this, appender); SendToAll(builder); - UpdateChannelInDB(); + _isDirty = true; } void Channel::SetMode(Player const* player, std::string const& p2n, bool mod, bool set) @@ -681,7 +674,7 @@ void Channel::Announce(Player const* player) SendToAll(builder); } - UpdateChannelInDB(); + _isDirty = true; } void Channel::Say(ObjectGuid guid, std::string const& what, uint32 lang) const @@ -813,7 +806,7 @@ void Channel::SetOwner(ObjectGuid guid, bool exclaim) SendToAll(ownerBuilder); } - UpdateChannelInDB(); + _isDirty = true; } } diff --git a/src/server/game/Chat/Channels/Channel.h b/src/server/game/Chat/Channels/Channel.h index 534b595ae21..31eb8d6fe21 100644 --- a/src/server/game/Chat/Channels/Channel.h +++ b/src/server/game/Chat/Channels/Channel.h @@ -21,6 +21,7 @@ #include "Common.h" #include "ObjectGuid.h" +#include <ctime> #include <map> #include <unordered_set> @@ -164,6 +165,10 @@ class TC_GAME_API Channel bool IsAnnounce() const { return _announceEnabled; } void SetAnnounce(bool announce) { _announceEnabled = announce; } + // will be saved to DB on next channel save interval + void SetDirty() { _isDirty = true; } + void UpdateChannelInDB(); + void SetPassword(std::string const& password) { _channelPassword = password; } bool CheckPassword(std::string const& password) const { return _channelPassword.empty() || (_channelPassword == password); } @@ -205,7 +210,6 @@ class TC_GAME_API Channel void JoinNotify(ObjectGuid guid) const; // invisible notify void LeaveNotify(ObjectGuid guid) const; // invisible notify void SetOwnership(bool ownership) { _ownershipEnabled = ownership; } - static void CleanOldChannelsInDB(); private: @@ -218,11 +222,9 @@ class TC_GAME_API Channel template<class Builder> void SendToOne(Builder& builder, ObjectGuid who) const; - bool IsOn(ObjectGuid who) const { return _playersStore.count(who) != 0; } - bool IsBanned(ObjectGuid guid) const { return _bannedStore.count(guid) != 0; } - - void UpdateChannelInDB() const; - void UpdateChannelUseageInDB() const; + bool IsOn(ObjectGuid who) const { return _playersStore.find(who) != _playersStore.end(); } + bool IsBanned(ObjectGuid guid) const { return _bannedStore.find(guid) != _bannedStore.end(); } + uint8 GetPlayerFlags(ObjectGuid guid) const { @@ -236,9 +238,11 @@ class TC_GAME_API Channel typedef std::map<ObjectGuid, PlayerInfo> PlayerContainer; typedef GuidUnorderedSet BannedContainer; + bool _isDirty; // whether the channel needs to be saved to DB + time_t _nextActivityUpdateTime; + bool _announceEnabled; //< Whether we should broadcast a packet whenever a player joins/exits the channel bool _ownershipEnabled; //< Whether the channel has to maintain an owner - bool _persistentChannel; //< Whether the channel is saved to DB bool _isOwnerInvisible; //< Whether the channel is owned by invisible GM, ownership should change to first player that joins channel uint8 _channelFlags; diff --git a/src/server/game/Chat/Channels/ChannelMgr.cpp b/src/server/game/Chat/Channels/ChannelMgr.cpp index ab93f9e396b..5fe43069310 100644 --- a/src/server/game/Chat/Channels/ChannelMgr.cpp +++ b/src/server/game/Chat/Channels/ChannelMgr.cpp @@ -34,7 +34,78 @@ ChannelMgr::~ChannelMgr() delete itr->second; } -ChannelMgr* ChannelMgr::forTeam(uint32 team) +/*static*/ void ChannelMgr::LoadFromDB() +{ + if (!sWorld->getBoolConfig(CONFIG_PRESERVE_CUSTOM_CHANNELS)) + { + TC_LOG_INFO("server.loading", ">> Loaded 0 custom chat channels. Custom channel saving is disabled."); + return; + } + + uint32 oldMSTime = getMSTime(); + if (uint32 days = sWorld->getIntConfig(CONFIG_PRESERVE_CUSTOM_CHANNEL_DURATION)) + { + PreparedStatement* stmt = CharacterDatabase.GetPreparedStatement(CHAR_DEL_OLD_CHANNELS); + stmt->setUInt32(0, days * DAY); + CharacterDatabase.Execute(stmt); + } + + QueryResult result = CharacterDatabase.Query("SELECT name, team, announce, ownership, password, bannedList FROM channels"); + if (!result) + { + TC_LOG_INFO("server.loading", ">> Loaded 0 custom chat channels. DB table `channels` is empty."); + return; + } + + std::vector<std::pair<std::string, uint32>> toDelete; + uint32 count = 0; + do + { + Field* fields = result->Fetch(); + std::string dbName = fields[0].GetString(); // may be different - channel names are case insensitive + uint32 team = fields[1].GetUInt32(); + bool dbAnnounce = fields[2].GetBool(); + bool dbOwnership = fields[3].GetBool(); + std::string dbPass = fields[4].GetString(); + std::string dbBanned = fields[5].GetString(); + + std::wstring channelName; + if (!Utf8toWStr(dbName, channelName)) + { + TC_LOG_ERROR("server.loading", "Failed to load custom chat channel '%s' from database - invalid utf8 sequence? Deleted.", dbName.c_str()); + toDelete.push_back({ dbName, team }); + continue; + } + + ChannelMgr* mgr = forTeam(team); + if (!mgr) + { + TC_LOG_ERROR("server.loading", "Failed to load custom chat channel '%s' from database - invalid team %u. Deleted.", dbName.c_str()); + toDelete.push_back({ dbName, team }); + continue; + } + + Channel* channel = new Channel(dbName, team, dbBanned); + channel->SetAnnounce(dbAnnounce); + channel->SetOwnership(dbOwnership); + channel->SetPassword(dbPass); + ASSERT_NOTNULL(forTeam(team))->_customChannels.emplace(channelName, channel); + + ++count; + } while (result->NextRow()); + + for (auto pair : toDelete) + { + PreparedStatement* stmt = CharacterDatabase.GetPreparedStatement(CHAR_DEL_CHANNEL); + stmt->setString(0, pair.first); + stmt->setUInt32(1, pair.second); + CharacterDatabase.Execute(stmt); + } + + TC_LOG_INFO("server.loading", ">> Loaded %u custom chat channels in %u ms", count, GetMSTimeDiffToNow(oldMSTime)); +} + +/*static*/ ChannelMgr* ChannelMgr::forTeam(uint32 team) { static ChannelMgr allianceChannelMgr(ALLIANCE); static ChannelMgr hordeChannelMgr(HORDE); @@ -74,6 +145,12 @@ Channel* ChannelMgr::GetChannelForPlayerByNamePart(std::string const& namePart, return nullptr; } +void ChannelMgr::SaveToDB() +{ + for (auto pair : _customChannels) + pair.second->UpdateChannelInDB(); +} + Channel* ChannelMgr::GetSystemChannel(uint32 channelId, AreaTableEntry const* zoneEntry) { ChatChannelsEntry const* channelEntry = sChatChannelsStore.AssertEntry(channelId); @@ -105,21 +182,13 @@ Channel* ChannelMgr::CreateCustomChannel(std::string const& name) return nullptr; Channel* newChannel = new Channel(name, _team); - - if (sWorld->getBoolConfig(CONFIG_PRESERVE_CUSTOM_CHANNELS)) - { - PreparedStatement* stmt = CharacterDatabase.GetPreparedStatement(CHAR_INS_CHANNEL); - stmt->setString(0, name); - stmt->setUInt32(1, _team); - CharacterDatabase.Execute(stmt); - TC_LOG_DEBUG("chat.system", "Channel(%s) saved in database", name.c_str()); - } + newChannel->SetDirty(); c = newChannel; return newChannel; } -Channel* ChannelMgr::GetCustomChannel(std::string const& name) +Channel* ChannelMgr::GetCustomChannel(std::string const& name) const { std::wstring channelName; if (!Utf8toWStr(name, channelName)) @@ -129,28 +198,6 @@ Channel* ChannelMgr::GetCustomChannel(std::string const& name) auto itr = _customChannels.find(channelName); if (itr != _customChannels.end()) return itr->second; - else if (sWorld->getBoolConfig(CONFIG_PRESERVE_CUSTOM_CHANNELS)) - { - PreparedStatement* stmt = CharacterDatabase.GetPreparedStatement(CHAR_SEL_CHANNEL); - stmt->setString(0, name); - stmt->setUInt32(1, _team); - if (PreparedQueryResult result = CharacterDatabase.Query(stmt)) - { - Field* fields = result->Fetch(); - std::string dbName = fields[0].GetString(); // may be different - channel names are case insensitive - bool dbAnnounce = fields[1].GetBool(); - bool dbOwnership = fields[2].GetBool(); - std::string dbPass = fields[3].GetString(); - std::string dbBanned = fields[4].GetString(); - - Channel* channel = new Channel(dbName, _team, dbBanned); - channel->SetAnnounce(dbAnnounce); - channel->SetOwnership(dbOwnership); - channel->SetPassword(dbPass); - _customChannels.emplace(channelName, channel); - return channel; - } - } return nullptr; } diff --git a/src/server/game/Chat/Channels/ChannelMgr.h b/src/server/game/Chat/Channels/ChannelMgr.h index d34e34ae47b..337069a37a1 100644 --- a/src/server/game/Chat/Channels/ChannelMgr.h +++ b/src/server/game/Chat/Channels/ChannelMgr.h @@ -38,12 +38,14 @@ class TC_GAME_API ChannelMgr ~ChannelMgr(); public: + static void LoadFromDB(); static ChannelMgr* forTeam(uint32 team); static Channel* GetChannelForPlayerByNamePart(std::string const& namePart, Player* playerSearcher); + void SaveToDB(); Channel* GetSystemChannel(uint32 channelId, AreaTableEntry const* zoneEntry = nullptr); Channel* CreateCustomChannel(std::string const& name); - Channel* GetCustomChannel(std::string const& name); + Channel* GetCustomChannel(std::string const& name) const; Channel* GetChannel(uint32 channelId, std::string const& name, Player* player, bool pkt = true, AreaTableEntry const* zoneEntry = nullptr) const; void LeftChannel(std::string const& name); void LeftChannel(uint32 channelId, AreaTableEntry const* zoneEntry); diff --git a/src/server/game/Entities/Player/Player.cpp b/src/server/game/Entities/Player/Player.cpp index 703f8e29beb..0ffc9ba31b4 100644 --- a/src/server/game/Entities/Player/Player.cpp +++ b/src/server/game/Entities/Player/Player.cpp @@ -20259,7 +20259,7 @@ void Player::UpdateSpeakTime() bool Player::CanSpeak() const { - return GetSession()->m_muteTime <= time (nullptr); + return GetSession()->m_muteTime <= GameTime::GetGameTime(); } /*********************************************************/ diff --git a/src/server/game/World/World.cpp b/src/server/game/World/World.cpp index 973fd3fac26..2e6cd80558a 100644 --- a/src/server/game/World/World.cpp +++ b/src/server/game/World/World.cpp @@ -30,7 +30,7 @@ #include "BattlefieldMgr.h" #include "BattlegroundMgr.h" #include "CalendarMgr.h" -#include "Channel.h" +#include "ChannelMgr.h" #include "CharacterCache.h" #include "CharacterDatabaseCleaner.h" #include "Chat.h" @@ -679,6 +679,7 @@ void World::LoadConfigSettings(bool reload) m_int_configs[CONFIG_MAIL_LEVEL_REQ] = sConfigMgr->GetIntDefault("LevelReq.Mail", 1); m_bool_configs[CONFIG_PRESERVE_CUSTOM_CHANNELS] = sConfigMgr->GetBoolDefault("PreserveCustomChannels", false); m_int_configs[CONFIG_PRESERVE_CUSTOM_CHANNEL_DURATION] = sConfigMgr->GetIntDefault("PreserveCustomChannelDuration", 14); + m_int_configs[CONFIG_PRESERVE_CUSTOM_CHANNEL_INTERVAL] = sConfigMgr->GetIntDefault("PreserveCustomChannelInterval", 5); m_bool_configs[CONFIG_GRID_UNLOAD] = sConfigMgr->GetBoolDefault("GridUnload", true); m_bool_configs[CONFIG_BASEMAP_LOAD_GRIDS] = sConfigMgr->GetBoolDefault("BaseMapLoadAllGrids", false); if (m_bool_configs[CONFIG_BASEMAP_LOAD_GRIDS] && m_bool_configs[CONFIG_GRID_UNLOAD]) @@ -2076,6 +2077,8 @@ void World::SetInitialWorldSettings() m_timers[WUPDATE_WHO_LIST].SetInterval(5 * IN_MILLISECONDS); // update who list cache every 5 seconds + m_timers[WUPDATE_CHANNEL_SAVE].SetInterval(getIntConfig(CONFIG_PRESERVE_CUSTOM_CHANNEL_INTERVAL) * MINUTE * IN_MILLISECONDS); + //to set mailtimer to return mails every day between 4 and 5 am //mailtimer is increased when updating auctions //one second is 1000 -(tested on win system) @@ -2103,8 +2106,8 @@ void World::SetInitialWorldSettings() TC_LOG_INFO("server.loading", "Initialize AuctionHouseBot..."); sAuctionBot->Initialize(); - // Delete all custom channels which haven't been used for PreserveCustomChannelDuration days. - Channel::CleanOldChannelsInDB(); + TC_LOG_INFO("server.loading", "Initializing chat channels..."); + ChannelMgr::LoadFromDB(); TC_LOG_INFO("server.loading", "Initializing Opcodes..."); opcodeTable.Initialize(); @@ -2280,6 +2283,20 @@ void World::Update(uint32 diff) sWhoListStorageMgr->Update(); } + if (m_timers[WUPDATE_CHANNEL_SAVE].Passed()) + { + m_timers[WUPDATE_CHANNEL_SAVE].Reset(); + + if (sWorld->getBoolConfig(CONFIG_PRESERVE_CUSTOM_CHANNELS)) + { + ChannelMgr* mgr1 = ASSERT_NOTNULL(ChannelMgr::forTeam(ALLIANCE)); + mgr1->SaveToDB(); + ChannelMgr* mgr2 = ASSERT_NOTNULL(ChannelMgr::forTeam(HORDE)); + if (mgr1 != mgr2) + mgr2->SaveToDB(); + } + } + /// Handle daily quests reset time if (currentGameTime > m_NextDailyQuestReset) { diff --git a/src/server/game/World/World.h b/src/server/game/World/World.h index a8dd0dfe04f..edf310c408b 100644 --- a/src/server/game/World/World.h +++ b/src/server/game/World/World.h @@ -82,6 +82,7 @@ enum WorldTimers WUPDATE_PINGDB, WUPDATE_CHECK_FILECHANGES, WUPDATE_WHO_LIST, + WUPDATE_CHANNEL_SAVE, WUPDATE_COUNT }; @@ -343,6 +344,7 @@ enum WorldIntConfigs CONFIG_MAX_RESULTS_LOOKUP_COMMANDS, CONFIG_DB_PING_INTERVAL, CONFIG_PRESERVE_CUSTOM_CHANNEL_DURATION, + CONFIG_PRESERVE_CUSTOM_CHANNEL_INTERVAL, CONFIG_PERSISTENT_CHARACTER_CLEAN_FLAGS, CONFIG_LFG_OPTIONSMASK, CONFIG_MAX_INSTANCES_PER_HOUR, diff --git a/src/server/worldserver/worldserver.conf.dist b/src/server/worldserver/worldserver.conf.dist index d7c8efe1c4d..dc3051a06df 100644 --- a/src/server/worldserver/worldserver.conf.dist +++ b/src/server/worldserver/worldserver.conf.dist @@ -1962,6 +1962,13 @@ PartyLevelReq = 1 PreserveCustomChannels = 1 # +# PreserveCustomChannelInterval +# Description: Interval (in minutes) at which custom channel data is saved to the database +# Default: 5 minutes + +PreserveCustomChannelInterval = 5 + +# # PreserveCustomChannelDuration # Description: Time (in days) that needs to pass before the customs chat channels get # cleaned up from the database. Only channels with ownership handout enabled |