diff --git a/trunk/dist/game/config/Server.ini b/trunk/dist/game/config/Server.ini index 00c95d1170..a2059efd9d 100644 --- a/trunk/dist/game/config/Server.ini +++ b/trunk/dist/game/config/Server.ini @@ -133,3 +133,27 @@ ClanNameTemplate = .* # Maximum number of characters per account. # Default: 7 (client limit) CharMaxNumber = 7 + + +# --------------------------------------------------------------------------- +# Scheduled Server Restart +# --------------------------------------------------------------------------- + +# Enable disable scheduled server restart. +# Default: False +ServerRestartSchedule = False + +# Send a message when player enters the game. +# Default: False +ServerRestartScheduleMessage = False + +# Restart time countdown (in seconds). +# Default: 300 (5 minutes) +ServerRestartScheduleCountdown = 300 + +# Scheduled restart hours. +# If you put 12:00 the server countdown for the restart will start at that time. +# After 5 minutes (300 seconds) the server will be restarted. +# You can put more than one value separated by commas (,). +# Example: 12:00,00:00 +ServerRestartScheduleHours = 07:00 diff --git a/trunk/java/com/l2jmobius/Config.java b/trunk/java/com/l2jmobius/Config.java index 0d88876a1e..744a9c2d36 100644 --- a/trunk/java/com/l2jmobius/Config.java +++ b/trunk/java/com/l2jmobius/Config.java @@ -989,6 +989,10 @@ public final class Config public static boolean SERVER_LIST_BRACKET; public static boolean LOGIN_SERVER_SCHEDULE_RESTART; public static long LOGIN_SERVER_SCHEDULE_RESTART_TIME; + public static boolean SERVER_RESTART_SCHEDULE; + public static boolean SERVER_RESTART_SCHEDULE_MESSAGE; + public static int SERVER_RESTART_SCHEDULE_COUNTDOWN; + public static String[] SERVER_RESTART_SCHEDULE_HOURS; // -------------------------------------------------- // MMO Settings @@ -1224,6 +1228,11 @@ public final class Config SERVER_LIST_AGE = serverSettings.getInt("ServerListAge", 0); SERVER_LIST_BRACKET = serverSettings.getBoolean("ServerListBrackets", false); + SERVER_RESTART_SCHEDULE = serverSettings.getBoolean("ServerRestartSchedule", false); + SERVER_RESTART_SCHEDULE_MESSAGE = serverSettings.getBoolean("ServerRestartScheduleMessage", false); + SERVER_RESTART_SCHEDULE_COUNTDOWN = serverSettings.getInt("ServerRestartScheduleCountdown", 300); + SERVER_RESTART_SCHEDULE_HOURS = serverSettings.getString("ServerRestartScheduleHours", "00:00").split(","); + try { DATAPACK_ROOT = new File(serverSettings.getString("DatapackRoot", ".").replaceAll("\\\\", "/")).getCanonicalFile(); diff --git a/trunk/java/com/l2jmobius/gameserver/GameServer.java b/trunk/java/com/l2jmobius/gameserver/GameServer.java index e8bf7841ff..857bd637ef 100644 --- a/trunk/java/com/l2jmobius/gameserver/GameServer.java +++ b/trunk/java/com/l2jmobius/gameserver/GameServer.java @@ -132,6 +132,7 @@ import com.l2jmobius.gameserver.instancemanager.PremiumManager; import com.l2jmobius.gameserver.instancemanager.PunishmentManager; import com.l2jmobius.gameserver.instancemanager.QuestManager; import com.l2jmobius.gameserver.instancemanager.RaidBossSpawnManager; +import com.l2jmobius.gameserver.instancemanager.ServerRestartManager; import com.l2jmobius.gameserver.instancemanager.SiegeManager; import com.l2jmobius.gameserver.instancemanager.WalkingManager; import com.l2jmobius.gameserver.instancemanager.ZoneManager; @@ -458,6 +459,11 @@ public final class GameServer System.exit(1); } + if (Config.SERVER_RESTART_SCHEDULE) + { + ServerRestartManager.getInstance(); + } + LoginServerThread.getInstance().start(); Toolkit.getDefaultToolkit().beep(); } diff --git a/trunk/java/com/l2jmobius/gameserver/Shutdown.java b/trunk/java/com/l2jmobius/gameserver/Shutdown.java index 5de39cf04e..21f9ec6aab 100644 --- a/trunk/java/com/l2jmobius/gameserver/Shutdown.java +++ b/trunk/java/com/l2jmobius/gameserver/Shutdown.java @@ -307,7 +307,14 @@ public class Shutdown extends Thread { _shutdownMode = restart ? GM_RESTART : GM_SHUTDOWN; - _log.warning("GM: " + activeChar.getName() + "(" + activeChar.getObjectId() + ") issued shutdown command. " + MODE_TEXT[_shutdownMode] + " in " + seconds + " seconds!"); + if (activeChar != null) + { + _log.warning("GM: " + activeChar.getName() + "(" + activeChar.getObjectId() + ") issued shutdown command. " + MODE_TEXT[_shutdownMode] + " in " + seconds + " seconds!"); + } + else + { + _log.warning("Server scheduled restart issued shutdown command. Restart in " + seconds + " seconds!"); + } if (_shutdownMode > 0) { diff --git a/trunk/java/com/l2jmobius/gameserver/instancemanager/ServerRestartManager.java b/trunk/java/com/l2jmobius/gameserver/instancemanager/ServerRestartManager.java new file mode 100644 index 0000000000..8c30d09b69 --- /dev/null +++ b/trunk/java/com/l2jmobius/gameserver/instancemanager/ServerRestartManager.java @@ -0,0 +1,107 @@ +/* + * This file is part of the L2J Mobius project. + * + * This program is free software: you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation, either version 3 of the License, or + * (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program. If not, see . + */ +package com.l2jmobius.gameserver.instancemanager; + +import java.text.SimpleDateFormat; +import java.util.Calendar; +import java.util.logging.Logger; + +import com.l2jmobius.Config; +import com.l2jmobius.gameserver.Shutdown; +import com.l2jmobius.gameserver.ThreadPoolManager; + +/** + * @author Gigi + */ +public class ServerRestartManager +{ + static final Logger _log = Logger.getLogger(ServerRestartManager.class.getName()); + + private String nextRestartString = "unknown"; + + protected ServerRestartManager() + { + try + { + final Calendar currentTime = Calendar.getInstance(); + final Calendar restartTime = currentTime; + Calendar lastRestart = currentTime; + restartTime.setLenient(true); + long delay = 0; + long lastDelay = 0; + int count = 0; + + for (String timeOfDay : Config.SERVER_RESTART_SCHEDULE_HOURS) + { + final String[] splitTimeOfDay = timeOfDay.split(":"); + restartTime.set(Calendar.HOUR_OF_DAY, Integer.parseInt(splitTimeOfDay[0])); + restartTime.set(Calendar.MINUTE, Integer.parseInt(splitTimeOfDay[1])); + restartTime.set(Calendar.SECOND, 00); + + if (restartTime.getTimeInMillis() < currentTime.getTimeInMillis()) + { + restartTime.add(Calendar.DAY_OF_MONTH, 1); + } + + delay = restartTime.getTimeInMillis() - currentTime.getTimeInMillis(); + if (count == 0) + { + lastDelay = delay; + lastRestart = restartTime; + } + if (delay < lastDelay) + { + lastDelay = delay; + lastRestart = restartTime; + } + count++; + } + + nextRestartString = new SimpleDateFormat("HH:mm").format(lastRestart.getTime()); + ThreadPoolManager.getInstance().scheduleGeneral(new ServerRestartTask(), lastDelay); + _log.info("Scheduled server restart at " + lastRestart.getTime().toString() + "."); + } + catch (Exception e) + { + _log.info("The scheduled server restart config is not set properly, please correct it!"); + } + } + + public String getNextRestartTime() + { + return nextRestartString; + } + + class ServerRestartTask implements Runnable + { + @Override + public void run() + { + Shutdown.getInstance().startShutdown(null, Config.SERVER_RESTART_SCHEDULE_COUNTDOWN, true); + } + } + + public static ServerRestartManager getInstance() + { + return SingletonHolder._instance; + } + + private static class SingletonHolder + { + protected static final ServerRestartManager _instance = new ServerRestartManager(); + } +} \ No newline at end of file diff --git a/trunk/java/com/l2jmobius/gameserver/network/clientpackets/EnterWorld.java b/trunk/java/com/l2jmobius/gameserver/network/clientpackets/EnterWorld.java index 5c70ba63c7..88ef633831 100644 --- a/trunk/java/com/l2jmobius/gameserver/network/clientpackets/EnterWorld.java +++ b/trunk/java/com/l2jmobius/gameserver/network/clientpackets/EnterWorld.java @@ -24,6 +24,7 @@ import com.l2jmobius.gameserver.data.sql.impl.OfflineTradersTable; import com.l2jmobius.gameserver.data.xml.impl.AdminData; import com.l2jmobius.gameserver.data.xml.impl.BeautyShopData; import com.l2jmobius.gameserver.data.xml.impl.SkillTreesData; +import com.l2jmobius.gameserver.enums.ChatType; import com.l2jmobius.gameserver.enums.Race; import com.l2jmobius.gameserver.enums.SubclassInfoType; import com.l2jmobius.gameserver.instancemanager.CHSiegeManager; @@ -37,6 +38,7 @@ import com.l2jmobius.gameserver.instancemanager.InstanceManager; import com.l2jmobius.gameserver.instancemanager.MailManager; import com.l2jmobius.gameserver.instancemanager.PetitionManager; import com.l2jmobius.gameserver.instancemanager.QuestManager; +import com.l2jmobius.gameserver.instancemanager.ServerRestartManager; import com.l2jmobius.gameserver.instancemanager.SiegeManager; import com.l2jmobius.gameserver.model.L2Clan; import com.l2jmobius.gameserver.model.L2Object; @@ -64,6 +66,7 @@ import com.l2jmobius.gameserver.network.SystemMessageId; import com.l2jmobius.gameserver.network.serverpackets.AcquireSkillList; import com.l2jmobius.gameserver.network.serverpackets.ActionFailed; import com.l2jmobius.gameserver.network.serverpackets.AllyCrest; +import com.l2jmobius.gameserver.network.serverpackets.CreatureSay; import com.l2jmobius.gameserver.network.serverpackets.Die; import com.l2jmobius.gameserver.network.serverpackets.EtcStatusUpdate; import com.l2jmobius.gameserver.network.serverpackets.ExAcquireAPSkillList; @@ -502,6 +505,11 @@ public class EnterWorld extends L2GameClientPacket AnnouncementsTable.getInstance().showAnnouncements(activeChar); + if ((Config.SERVER_RESTART_SCHEDULE) && (Config.SERVER_RESTART_SCHEDULE_MESSAGE)) + { + activeChar.sendPacket(new CreatureSay(2, ChatType.BATTLEFIELD, "[SERVER]", "Next restart is scheduled at " + ServerRestartManager.getInstance().getNextRestartTime() + ".")); + } + if (showClanNotice) { final NpcHtmlMessage notice = new NpcHtmlMessage();