Panel: unticking 'web panel enabled' + restart panel really turns it off (2.9.5)

The restart used to refuse when the panel was disabled, so it stayed
reachable. Now it stops the panel (also the relay on the game port);
'panel on|off' in the console turns it on/off and saves server.json.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
This commit is contained in:
2026-10-02 21:07:18 +02:00
co-authored by Claude Opus 5.5
parent 905d191807
commit 835d3ce998
6 changed files with 67 additions and 6 deletions
+8 -1
View File
@@ -667,7 +667,14 @@ public sealed class AdminPanel
{
var fresh = host.LoadConfigForRestart();
if (fresh == null) return Error(500, "Could not read server.json");
if (!fresh.PanelEnabled) return Error(400, "The panel is turned off in the settings - turn it on again or edit server.json by hand");
if (!fresh.PanelEnabled)
{
// "Web-Panel an" abgehakt: das Panel wird wirklich ausgeschaltet
GameServer.Log($"[panel] {by} turns the web panel off");
_ = Task.Run(async () => { await Task.Delay(700); host.RestartPanel(fresh, by); });
return Results.Json(new { ok = true, disabled = true,
message = "The web panel is turned off - turn it on again with 'panel on' in the server console or PanelEnabled in server.json" });
}
bool shares = fresh.PanelPort <= 0 || fresh.PanelPort == fresh.Port;
int port = shares ? fresh.Port : fresh.PanelPort;
string basePath = (fresh.PanelBasePath ?? "").Trim().TrimEnd('/');
+4 -2
View File
@@ -1012,8 +1012,10 @@ public sealed class GameServer
SaveWorld();
break;
case "panel":
if (Panel != null) Panel.PrintInfo();
else Log("The web panel is disabled (PanelEnabled in server.json)");
if (args.Length > 1 && (args[1] == "on" || args[1] == "off") && Host != null)
Log(Host.SetPanelEnabled(args[1] == "on", "Console"));
else if (Panel != null) Panel.PrintInfo();
else Log("The web panel is disabled - 'panel on' turns it on");
break;
case "reset-world":
ResetWorld("Console");
+1 -1
View File
@@ -7,7 +7,7 @@
<ImplicitUsings>enable</ImplicitUsings>
<RootNamespace>MSCO.Server</RootNamespace>
<AssemblyName>MSCO.Server</AssemblyName>
<Version>2.9.4</Version>
<Version>2.9.5</Version>
<Company>MBM</Company>
<Product>MSCO Dedicated Server</Product>
<InvariantGlobalization>true</InvariantGlobalization>
+5
View File
@@ -323,6 +323,11 @@ async function restartPanel() {
if (!ok) return;
const r = await act(api("POST", "server/restart-panel"));
if (!r) return;
if (r.disabled) {
// Panel ausgeschaltet: nicht auf ein Neuladen warten
document.body.replaceChildren(h("div", { class: "empty" }, r.message));
return;
}
const target = r.url && r.url !== location.origin + location.pathname ? r.url : location.href;
// Warten, bis das Panel wieder antwortet, dann neu laden
const started = Date.now();
+3
View File
@@ -13,6 +13,9 @@
window.MSCO_LANG = lang;
const DE = {
"The web panel is turned off - turn it on again with 'panel on' in the server console or PanelEnabled in server.json":
"Das Web-Panel ist ausgeschaltet - wieder an mit 'panel on' in der Server-Konsole oder PanelEnabled in server.json",
// Neues Spiel
"New game": "Neues Spiel",
"Start a completely fresh My Summer Car game instead of an uploaded save. The current save game is backed up first. The first player to join creates the new world.":
+46 -2
View File
@@ -111,7 +111,9 @@ public sealed class ServerHost
{
bool portChanged = fresh.Port != listenerPort;
Config = fresh;
Panel?.RestartWeb(fresh);
if (!fresh.PanelEnabled) { StopPanel(by); return; } // "Web-Panel an" abgehakt: wirklich ausschalten
if (Panel == null) StartPanel();
else Panel.RestartWeb(fresh);
if (!portChanged) return;
if (Server != null && State == HostState.Running) RequestRestart(by); // bindet beim Start den neuen Port
else Listen(fresh.Port);
@@ -132,6 +134,43 @@ public sealed class ServerHost
RequestExit();
}
/// <summary>Web-Panel ausschalten (Einstellung abgehakt + "Panel neu starten" oder Konsole "panel off").</summary>
public void StopPanel(string by)
{
if (Panel == null) return;
GameServer.Log($"Web panel turned off by {by} - turn it on again with 'panel on' in the console or PanelEnabled in server.json");
var panel = Panel;
Panel = null;
if (Server != null) Server.Panel = null;
try { panel.Stop(); } catch { }
}
void StartPanel()
{
Panel = AdminPanel.Start(this, Config, dataDir);
if (Server != null) Server.Panel = Panel;
}
/// <summary>Konsole "panel on|off": Einstellung speichern und Panel starten bzw. stoppen.</summary>
public string SetPanelEnabled(bool enabled, string by)
{
if (!offline)
{
try
{
var fresh = ServerConfig.LoadOrCreate(configPath, out _);
fresh.PanelEnabled = enabled;
fresh.Save(configPath);
}
catch (Exception e) { return "Could not save server.json: " + e.Message; }
}
Config.PanelEnabled = enabled;
if (!enabled) { StopPanel(by); return "Web panel turned off"; }
if (Panel == null) StartPanel();
Panel?.PrintInfo();
return "Web panel turned on";
}
/// <summary>Ganzes Programm beenden (Strg+C, docker stop, "exit").</summary>
public void RequestExit()
{
@@ -229,8 +268,13 @@ public sealed class ServerHost
GameServer.Log("The server is not running ('exit' quits the program)");
break;
case "panel":
if (Panel != null) Panel.PrintInfo(); else GameServer.Log("The web panel is disabled");
{
string arg = cmd.Split(' ').Length > 1 ? cmd.Split(' ')[1].ToLowerInvariant() : "";
if (arg == "on" || arg == "off") GameServer.Log(SetPanelEnabled(arg == "on", "Console"));
else if (Panel != null) Panel.PrintInfo();
else GameServer.Log("The web panel is disabled - 'panel on' turns it on");
break;
}
case "status":
GameServer.Log($"Server {State.ToString().ToLower()}" + (LastError != null ? ": " + LastError : ""));
break;