CS2 Mapveto als ein Container (Dockerfile, compose.yml, Anleitung)

Ein Image mit Webseite, Backend, SQLite und Docker-Client; startet
Match-Container über /var/run/docker.sock auf demselben Host. Tests
laufen beim Bauen mit. Auf amp-cluster gebaut (301 MB) und geprüft.

Dazu: Testbefehl für Node 22 angepasst, beim Beenden werden ausstehende
Live-Updates verworfen und laufende Server-Aktionen abgewartet, damit nach
dem Schließen der Datenbank nichts mehr darauf zugreift.
This commit is contained in:
mregosar committed 2026-10-25 22:40:52 +01:00
1 parent e3a1ed4a63
commit 1b7c13b592
9 files changed
+236 -1

No files matched your search

+3
View File
@@ -52,6 +52,9 @@ export function createApp(config, { adapter: adapterOverride, logger = console }
},
async close() {
manager.stopLoops();
// Laufende Server-Aktionen (Start, Konfiguration) kurz abwarten, bevor die Datenbank schließt
await manager.idle(5000);
io.disposeRealtime();
io.close();
await new Promise((resolve) => server.close(() => resolve()));
db.close();
+9
View File
@@ -111,5 +111,14 @@ export function attachRealtime(httpServer, { service, config }) {
});
});
// Beim Herunterfahren: ausstehende Sammel-Updates verwerfen, damit nichts mehr auf die Datenbank zugreift
io.disposeRealtime = () => {
clearTimeout(overviewTimer);
clearTimeout(streamTimer);
for (const t of pending.values()) clearTimeout(t);
pending.clear();
service.removeAllListeners('changed');
};
return io;
}
+6
View File
@@ -86,6 +86,12 @@ export class ServerManager {
this.timers.push(setInterval(() => this.reap().catch((e) => this.logger.error(e)), this.config.reaperIntervalSeconds * 1000));
}
/** Wartet, bis keine Server-Aktion mehr läuft (höchstens timeoutMs). */
async idle(timeoutMs = 5000) {
const deadline = Date.now() + timeoutMs;
while (this.busy.size > 0 && Date.now() < deadline) await new Promise((r) => setTimeout(r, 50));
}
stopLoops() {
this.simulator.stopAll();
for (const t of this.autoAdvance.values()) clearTimeout(t);