Anleitung für einen eigenen dedizierten OpenTTD Server

Dedizierten OpenTTD-Server einrichten. Anleitung mit Docker für multiplayer-fähiges Transport Tycoon – kostenlos und selbst gehostet. Jetzt Server aufsetzen!

Veröffentlicht am Aktualisiert am
Anleitung für einen eigenen dedizierten OpenTTD Server hero image
Inhalt

Einführung zu OpenTTD

Vor einigen Jahren habe ich nach Spielen gesucht, die ich zusammen mit Freunden spielen könnte, ohne dabei am gleichen Ort zu sein. Eins der Spiele, auf die ich dabei gestoßen bin, ist OpenTTD.

OpenTTD ist ein Open-Source-Simulationsspiel, das auf Transport Tycoon Deluxe basiert

Dieses kostenlose Spiel ist auch über Steam oder den Play Store zu finden und hat äußerst positive Bewertungen (96 %) respektive 4,1/5 Sterne. In diesem strategischen Transport Tycoon Spiel geht es darum, ein Transportunternehmen durch den Bau und die Verwaltung von Transportwegen und Transportfahrzeugen zu leiten. Man kann Züge, Busse, Flugzeuge und Schiffe einsetzen, um Waren zu transportieren und die Industrie zu erweitern.

Warum einen dedizierten Server betreiben?

Durch einen dedizierten OpenTTD Server st es möglich, dass mehrere Spieler zu unterschiedlichen Zeiten in ein gemeinsames Spiel einloggen können, ohne dass der Host selbst online sein muss. In dieser Anleitung zeige ich, wie man einen eigenen dedizierten OpenTTD Server mieten und betreiben kann, der rund um die Uhr verfügbar ist.

Wer lieber ein Video sehen möchte, kann sich das Tutorial auf YouTube ansehen.

Server mieten

Wer bereits einen Server nach dieser Anleitung eingerichtet hat, kann diesen Teil überspringen, da hier die Einrichtung in gekürzter Form wiederholt wird.

Der erste Schritt besteht darin, sich einen geeigneten Server zu mieten. Empfehlenswert sind meiner Meinung die VPS und insbesondere auch Root-Server (dedizierte CPU) von Netcup oder die Server von Hetzner. Für einen reinen OpenTTD-Server braucht man keine hohen Anforderungen, hauptsächlich dann, wenn nicht riesige Karten erstellt werden sollen und/oder eine hohe Spieleranzahl erwartet wird. Ein kleinerer VPS sollte vollkommen ausreichen.

Neukunden erhalten mit diesen Affiliate-Gutscheinen einen Rabatt auf die erste Bestellung (und ich eine Provision für geworbene Kunden). Die prozentualen Rabatte bleiben dauerhaft aktiv, solange der VPS nicht gekündigt wird.

Als Betriebssystem wähle ich bei der Neuinstallation Ubuntu 24.04 aus. Ein anderes Betriebssystem wäre auch möglich, solange Docker darauf installiert werden kann, aber ich habe einige Erfahrung mit Ubuntu und sehe keinen Grund zu wechseln. Des Weiteren ist das Ende des Standard-Supports erst im April 2029, somit wird es vermutlich erst mal nicht nötig sein, das Betriebssystem auf die nächste Version zu upgraden.

Ubuntu Server einrichten

Sobald der Server mit der Neuinstallation fertig ist, muss die Verbindung zum Server hergestellt werden. Dies lässt sich unter Windows mit dem Windows Terminal, PuTTY oder einem ähnlichen Programm bewerkstelligen. Auch VSCode hat einen eingebauten Terminal und bietet den Vorteil der leichteren Bearbeitung, wie hier beschrieben. Ich nutze das Windows Terminal.

Terminal

Terminalbash
ssh root@{ip-Adresse}

Es sollte selbstverständlich die eigene IP-Adresse des Servers eingetragen werden.

Anschließend gegebenenfalls die Frage mit „yes“ beantworten und das Passwort eingeben. Während der Eingabe wird das Passwort nicht angezeigt. Als Erstes schauen wir, ob es Updates gibt und installieren diese gegebenenfalls:

Terminalbash
apt update
apt upgrade

Die Frage, ob man updaten möchte mit Y bestätigen.

Der Texteditor Nano sollte schon standardmäßig installiert sein, aber zur Sicherheit kann man ihn so installieren:

Terminalbash
apt install nano

Als Nächstes benennen wir den Server um:

Terminalbash
nano /etc/hostname

Hostname

In Nano wird die Datei mit Strg + X verlassen. Nano wird euch Fragen, ob ihr die Änderungen speichern wollt (mit Y bestätigen) und wie ihr die Datei nennen wollt. Da wir sie überschreiben möchten, ändern wir den Namen nicht und bestätigen einfach mit Enter.

Sobald du den Server neu startest reboot und dich anschließend wieder mit ihm verbindest ssh admin@{ip-Adresse} ist der neue Host-Name sichtbar.

Neuer Hostname

Nun ist es sinnvoll einen Nutzer anzulegen, der nicht root ist.

Terminalbash
useradd -m -G sudo namedesneuennutzers
passwd namedesneuennutzers

Useradd ist der Befehl, um einen neuen Nutzer anzulegen. Das -m sorgt dafür, dass dieser Nutzer einen Home-Ordner eingerichtet bekommt. Das -G packt den Nutzer in eine Gruppe, anschließend wird die Gruppe genannt. Die Sudo Gruppe darf Befehle mit sudo ausführen. Zuletzt folgt der Name des neuen Nutzers. Mit passwd wird ein Password für den Nutzer erstellt.

Sollte die sudo Gruppe nicht existieren, musst du eine Gruppe erstellen.

Terminalbash
groupadd namederneuengruppe

Diese Gruppe sollte die Rechte haben Sudo-Befehle auszuführen:

Terminalbash
EDITOR=nano visudo

In der Datei muss dann die neue Gruppe erwähnt werden.

Gruppenverwaltung

Jetzt stellen wir bei Bedarf die richtige Zeit ein.

Terminalbash
date

Falls nicht die richtige Zeit angezeigt wird:

Terminalbash
tzselect

Über die Zahlen lässt sich die Zeitzone auswählen.

Terminalbash
timedatectl set-timezone 'Europe/Berlin'

Es ist an der Zeit den Server neu zu starten und sich als neu angelegter Nutzer anzumelden.

Terminalbash
reboot

Als Nächstes installieren wir Htop (ein Monitoring-Programm).

Terminalbash
apt install htop

Jetzt müsste der Server die Ausführung verweigern und fragen, ob man root sei.

Zugriff verweigert

Also noch mal mit Superuser do.

Terminalbash
sudo apt install htop

Über die Eingabe von htop kann man sich nun die Auslastung des Servers anschauen.

Damit lässt sich gut verfolgen, wie stark die CPU und der RAM des Servers beansprucht werden. Mit F10 oder STRG + C verlässt du die Ansicht wieder.

Ich möchte gerne noch eine andere Shell haben.

Terminalbash
sudo apt install git curl
sudo apt install zsh

Nun installiere ich zim und ändere die Standard-Shell auf zsh.

Terminalbash
curl -fsSL https://raw.githubusercontent.com/zimfw/install/master/install.zsh | zsh
chsh -s /bin/zsh
exec bash

Jetzt müsste die Shell (subjektiv) besser aussehen.

ZSH

Der wichtigste Part der Installation sind Docker und Docker-Compose. Außerdem optional noch Lazydocker, für eine sehr einfache Möglichkeit sich seine Docker-Container und deren aktuelle Logs über SSH anzusehen.

Terminalbash
# Add Docker's official GPG key:
sudo apt-get update
sudo apt-get install ca-certificates curl
sudo install -m 0755 -d /etc/apt/keyrings
sudo curl -fsSL https://download.docker.com/linux/ubuntu/gpg -o /etc/apt/keyrings/docker.asc
sudo chmod a+r /etc/apt/keyrings/docker.asc

# Add the repository to Apt sources:
echo \
  "deb [arch=$(dpkg --print-architecture) signed-by=/etc/apt/keyrings/docker.asc] https://download.docker.com/linux/ubuntu \
  $(. /etc/os-release && echo "${UBUNTU_CODENAME:-$VERSION_CODENAME}") stable" | \
  sudo tee /etc/apt/sources.list.d/docker.list > /dev/null
sudo apt-get update

# Install Docker:
sudo apt-get install docker-ce docker-ce-cli containerd.io docker-buildx-plugin docker-compose-plugin

Als Letztes richten wir einen Ordner im Heimverzeichnis des neuen Nutzers an

Terminalbash
cd ~
mkdir docker

Mit mkdir (make directory) haben wir den Ordner docker im Homeverzeichnis (~) erstellt.

Sollte sich Lazydocker öffnen lassen, ist die Einrichtung abgeschlossen.

Terminalbash
sudo lazydocker

Mit Q, ESC oder STRG + C lässt sich Lazydocker wieder beenden.

Docker-Compose mit OpenTTD

Der nächste Schritt ist das Erstellen einer Docker-Compose-Datei, durch die der Container mit OpenTTD gestartet wird. Zunächst benötigen wir einen Ordner, in dem die Konfigurationsdateien und die Spielstände gespeichert werden können, sowie die Docker-Compose-Datei:

Terminalbash
mkdir ~/docker/appdata/openttd -p
touch ~/docker/docker-compose-openttd.yml

Wir schauen nach, ob der Port 3979 bereits genutzt wird.

Terminalbash
sudo lsof -i -P -n | grep LISTEN

Wir befüllen jetzt die Docker-Compose Datei.

Terminalbash
nano ~/docker/docker-compose-openttd.yml
yaml
services:
    openttd:
        container_name: openttd
        image: ghcr.io/ropenttd/openttd:14
        ports:
            - 3979:3979/tcp
            - 3979:3979/udp
        restart: unless-stopped
        volumes:
            - ./appdata/openttd:/config
        environment:
            - loadgame=false

Sollte der Port 3979 bereits genutzt werden, wählen wir einen anderen Port, unter dem der Docker erreicht werden kann. Zum Beispiel 3969:3979/tcp und 3969:3979/udp. Das ist auch nötig, wenn mehrere Server gleichzeitig laufen sollen. Nachdem wir die Datei gespeichert haben, starten wir den Container.

Terminalbash
cd ~/docker
sudo docker compose -f docker-compose-openttd.yml up -d

Und wir schauen uns an, ob etwas Ungewöhnliches im Log steht.

Terminalbash
lazydocker

Auszug aus den Logs des Openttd-Containers

Zunächst stoppen wir unseren Container wieder.

Terminalbash
sudo docker compose -f docker-compose-openttd down

Der Container lässt sich auch über Lazydocker stoppen.

Bearbeiten der Konfiguration

Nun sollte die Konfiguration nach eigenem belieben angepasst werden. Die Konfigurationsdateien sollte beim ersten Start des Containers automatisch heruntergeladen worden sein.

Terminalbash
sudo nano ~/docker/appdata/openttd/private.cfg

Hier kann ich den Servernamen ändern.

Terminalbash
sudo nano ~/docker/appdata/openttd/secrets.cfg

Hier kann ich das Passwort für den Server ändern, wodurch neue Spieler erst das Passwort eingeben müssen, um mitspielen zu können.

Terminalbash
server_password = abc
Terminalbash
sudo nano ~/docker/appdata/openttd/openttd.cfg

Hier gibt es viele Möglichkeiten, ich ändere ein paar Werte der Standardeinstellungen:

Terminalbash
autosave_on_exit = true
autosave_on_network_disconnect = true

Das Spiel wird so automatisch gespeichert, wenn der Server beendet wird.

Terminalbash
min_active_clients = 1

Das Spiel wird pausiert, wenn nicht mindestens ein Spieler mit dem Server verbunden ist.

Terminalbash
map_x = 9 # 6 bis 12
map_y = 9 # 6 bis 12

Die Größe der Karte kann verändert werden. Je größer die Karte, umso mehr muss der Server arbeiten.

Terminalbash
infrastructure_maintenance = true

Dadurch wird in regelmäßigen Abständen ein Betrag gezahlt, der sich aus der Anzahl der Fläche mit Schienen, Kanälen oder Schleusen errechnet.

Terminalbash
max_aircraft = 100
max_ships = 200

Diese Einstellung verringert die Anzahl der Flugzeuge und Schiffe, die ein Unternehmen haben darf.

Terminalbash
town_name = german

Das sorgt für deutsche Städtenamen.

Terminalbash
terrain_type = 2

Das bringt eine etwas weniger flache Landschaft.

Terminalbash
snow_line_height = 7

Schnee fängt tiefer an.

Terminalbash
town_layout = 4

Abwechslungsreichere Städte

Terminalbash
industry_density = 4

Geringere Industriedichte

Terminalbash
station_noise_level = true

Mit dieser Einstellung ist die Anzahl der Flughäfen, die in der Nähe einer Stadt platziert werden können, nicht mehr festgelegt. Stattdessen hängt sie vom Lärmpegel der Flughäfen, ihrer Entfernung zum Stadtzentrum und der Einstellung der Stadt ab.

Den Rest lasse ich vorerst so, wie es ist. Jetzt lösche ich die bisherigen automatisch erstellten Spielstände.

Terminalbash
sudo rm -rf ~/docker/appdata/openttd/save

Starten des Spiels

Wir passen die Konfiguration an, damit Spielstände geladen werden.

Terminalbash
cd ~/docker
nano docker-compose-openttd.yml
yaml
services:
    openttd:
        container_name: openttd
        image: ghcr.io/ropenttd/openttd:14
        restart: unless-stopped
        ports:
            - 3979:3979/tcp
            - 3979:3979/udp
        volumes:
            - ./appdata/openttd:/config
        environment:
            - loadgame=exit

Und es kann ein neues Spiel gestartet werden.

Terminalbash
cd ~/docker
sudo docker compose -f docker-compose-openttd.yml up -d

Diesmal ist in den Logs zu sehen, dass das Spiel pausiert wurde, was an den veränderten Einstellungen liegt.

Spiel ist pausiert

Jetzt ist es auch möglich, sich mit dem Spiel zu verbinden. Dazu installieren wir das Spiel und starten es. Im Menü „Mehrspieler“ kann man einen Server hinzufügen.

Server hinzufügen

In das Eingabefeld muss die IP-Adresse inklusive Port eingegeben werden. Also zum Beispiel 191.80.90.90:3979. Anschließend kann man dem Server beitreten.

Spieleintritt

Update des Servers

Natürlich sollte man ab und an den Server aktualisieren, mit Docker ist das mit wenigen Zeilen Code erledigt, nachdem wir den Tag in der Docker-Compose-Datei aktualisiert haben.

Terminalbash
cd ~/docker
sudo docker compose -f docker-compose-openttd.yml pull
sudo docker compose -f docker-compose-openttd.yml down
sudo docker compose -f docker-compose-openttd.yml up -d

# Nicht vergessen auch mal den Host-Server zu updaten
sudo apt update && sudo apt upgrade

Über htop kann man sich ansehen, ob der Server ausreichend Resourcen hat. An dieser Stelle wünsche ich noch viel Spaß beim Bauen 🚈