HomeStart / GuidesAnleitungen / Running a trading bot on a Linux VPS 24/7/ Einen Trading-Bot 24/7 auf einem Linux-VPS betreiben

Running a trading bot on a Linux VPS 24/7: systemd, chrony, and a kill switch you've actually testedEinen Trading-Bot 24/7 auf einem Linux-VPS betreiben: systemd, chrony und ein Kill-Switch, den Sie wirklich getestet haben

A trading bot that only runs when your laptop is open is not a trading bot, it is a demo. Getting it onto a server that stays up is the easy part; the part that actually matters is boring operations work — restart policy, clock sync, and knowing the bot is still alive without staring at a terminal.Ein Trading-Bot, der nur läuft, wenn Ihr Laptop offen ist, ist kein Trading-Bot, sondern eine Demo. Ihn auf einen Server zu bringen, der durchläuft, ist der leichte Teil; was wirklich zählt, ist die langweilige Betriebsarbeit — Restart-Policy, Zeitsynchronisation und zu wissen, dass der Bot noch lebt, ohne die ganze Zeit auf ein Terminal zu starren.

What this covers, and what it doesn'tWas diese Anleitung abdeckt, und was nicht

This is an operations guide: running a Python trading bot as a long-lived Linux process that restarts sanely, keeps credentials off disk in the wrong place, agrees with the exchange about what time it is, and tells you when it dies. It does not cover strategy, order types, backtesting, or position sizing — that is your call to make, and nothing here is financial advice. Assume you already have a working bot that talks to an exchange's API and just need it to run unattended without becoming a liability.Das ist eine Betriebsanleitung: Sie zeigt, wie Sie einen Python-Trading-Bot als langlebigen Linux-Prozess betreiben, der sinnvoll neu startet, Credentials nicht am falschen Ort auf der Festplatte liegen lässt, sich mit der Börse über die Uhrzeit einig ist und Ihnen Bescheid gibt, wenn er stirbt. Sie behandelt nicht Strategie, Ordertypen, Backtesting oder Positionsgrößen — das ist Ihre Entscheidung, und nichts hier ist eine Finanzberatung. Gehen Sie davon aus, dass Sie bereits einen funktionierenden Bot haben, der mit der API einer Börse spricht, und dass er nur noch unbeaufsichtigt laufen soll, ohne zum Risiko zu werden.

Sizing the machineDie Maschine richtig dimensionieren

A single bot process is a light workload. A Python process holding a websocket connection, a small in-memory order book, and a logging pipeline typically sits well under 300 MB resident. The 1 GiB Starter tier covers one bot with headroom for the OS and chrony. What actually pushes you up a tier is running several bots on one box, keeping a local database of fills and candles that grows for months, or backtesting on the same machine you trade from — batch work and a live process fight over the same cores. Keep those separate if you can.Ein einzelner Bot-Prozess ist eine leichte Last. Ein Python-Prozess mit einer Websocket-Verbindung, einem kleinen Orderbuch im Speicher und einer Logging-Pipeline liegt typischerweise deutlich unter 300 MB resident. Die 1-GiB-Starter-Stufe deckt einen Bot mit Puffer für das Betriebssystem und chrony ab. Was Sie tatsächlich eine Stufe hochtreibt, ist, mehrere Bots auf einer Maschine zu betreiben, eine lokale Datenbank mit Fills und Candles zu führen, die über Monate wächst, oder auf derselben Maschine zu backtesten, von der aus Sie handeln — Batch-Arbeit und ein Live-Prozess konkurrieren dann um dieselben Kerne. Trennen Sie das, wenn Sie können.

Disk is rarely the constraint: a bot's code, a virtualenv, and months of rotated JSON logs fit inside a few gigabytes. The 25 GB on Starter is plenty unless you're recording full market data ticks, a different sizing conversation entirely.Speicherplatz ist selten der Engpass: Der Code eines Bots, ein virtualenv und Monate an rotierten JSON-Logs passen in wenige Gigabyte. Die 25 GB im Starter reichen locker, es sei denn, Sie zeichnen vollständige Markt-Ticks auf — das ist ein völlig anderes Dimensionierungsthema.

Step 1: a clean, outbound-only machineSchritt 1: eine saubere Maschine, nur ausgehend

Deploy an Ubuntu LTS image, then do the basics before anything touches the network: a non-root user, an SSH key, password login off, and a firewall that defaults to deny. Walkthroughs for both are at connect to your VPS over SSH and secure your VPS.Setzen Sie ein Ubuntu-LTS-Image auf und erledigen Sie dann die Grundlagen, bevor irgendetwas das Netzwerk berührt: einen Non-Root-User, einen SSH-Key, Passwort-Login aus, und eine Firewall, die standardmäßig blockiert. Anleitungen zu beidem finden Sie unter über SSH mit Ihrem VPS verbinden und Ihren VPS absichern.

This workload only calls out — REST calls and a websocket to the exchange, nothing listening for inbound connections — so the shared, NAT-style IPv4 most budget VPS plans hand out by default is irrelevant here. No dedicated address or forwarded port needed for anything in this guide.Diese Last ruft nur nach außen — REST-Aufrufe und ein Websocket zur Börse, nichts hört auf eingehende Verbindungen —, deshalb ist die geteilte, NAT-artige IPv4, die die meisten günstigen VPS-Tarife standardmäßig vergeben, hier irrelevant. Für nichts in dieser Anleitung brauchen Sie eine dedizierte Adresse oder einen weitergeleiteten Port.

Create a dedicated system user for the bot rather than running it as your own login or as root:Legen Sie einen eigenen System-User für den Bot an, statt ihn unter Ihrem eigenen Login oder als root laufen zu lassen:

sudo useradd --system --create-home --shell /usr/sbin/nologin botuser
sudo mkdir -p /opt/trading-bot/data
sudo chown -R botuser:botuser /opt/trading-bot

Deploy your code under /opt/trading-bot and build the virtualenv as botuser, not as yourself:Bringen Sie Ihren Code nach /opt/trading-bot und bauen Sie das virtualenv als botuser, nicht als Sie selbst:

sudo -u botuser python3 -m venv /opt/trading-bot/venv
sudo -u botuser /opt/trading-bot/venv/bin/pip install -r /opt/trading-bot/requirements.txt

Step 2: the bot as a systemd serviceSchritt 2: der Bot als systemd-Service

A bot running in a tmux session survives an SSH disconnect but not a reboot, a crash, or you forgetting which pane it's in. A systemd unit survives all three and gives you a restart policy for free:Ein Bot, der in einer tmux-Session läuft, übersteht einen SSH-Abbruch, aber keinen Reboot, keinen Crash und nicht, dass Sie vergessen, in welchem Pane er läuft. Eine systemd-Unit übersteht alle drei und gibt Ihnen eine Restart-Policy gratis dazu:

[Unit]
Description=trading-bot
After=network-online.target chrony.service
Wants=network-online.target
StartLimitIntervalSec=300
StartLimitBurst=5

[Service]
Type=simple
User=botuser
Group=botuser
WorkingDirectory=/opt/trading-bot
EnvironmentFile=/etc/trading-bot/env
ExecStart=/opt/trading-bot/venv/bin/python /opt/trading-bot/bot.py
Restart=on-failure
RestartSec=5
NoNewPrivileges=true
ProtectSystem=strict
ReadWritePaths=/opt/trading-bot/data
PrivateTmp=true

[Install]
WantedBy=multi-user.target

Two choices here are deliberate. StartLimitIntervalSec=300 with StartLimitBurst=5 stops a crash loop from hammering the exchange's API forever — after five restarts in five minutes, systemd gives up and leaves the unit stopped instead of retrying into a rate-limit ban. And Restart=on-failure, not Restart=always, only restarts the process on a non-zero exit status. That distinction is the whole point of the kill switch in Step 7, so hold onto it.Zwei Entscheidungen darin sind Absicht. StartLimitIntervalSec=300 mit StartLimitBurst=5 verhindert, dass eine Crash-Loop endlos auf die API der Börse einhämmert — nach fünf Neustarts in fünf Minuten gibt systemd auf und lässt die Unit gestoppt, statt sich in ein Rate-Limit-Verbot hineinzulaufen. Und Restart=on-failure, nicht Restart=always, startet den Prozess nur bei einem Exit-Status ungleich null neu. Genau diese Unterscheidung ist der ganze Sinn des Kill-Switches in Schritt 7, also merken Sie sie sich.

Enable it now. Don't start it yet — the unit's EnvironmentFile doesn't exist until Step 3, and systemd refuses to start a service whose EnvironmentFile is missing:Aktivieren Sie sie jetzt schon. Starten Sie sie aber noch nicht — die EnvironmentFile der Unit existiert erst ab Schritt 3, und systemd weigert sich, einen Service zu starten, dessen EnvironmentFile fehlt:

sudo systemctl daemon-reload
sudo systemctl enable trading-bot.service

The systemd.service manual documents every directive above if you want the exact semantics rather than my summary of them.Das systemd.service-Manual dokumentiert jede Direktive von oben, falls Sie die exakte Semantik wollen statt meiner Zusammenfassung.

Step 3: API keys in a root-only file, never in the repoSchritt 3: API-Keys in einer Datei nur für root, nie im Repo

The exchange API key and secret don't belong in your code, in a .env committed by accident, or in a config file readable by every user on the box. They belong in an EnvironmentFile only root can read:Der API-Key und das Secret der Börse gehören nicht in Ihren Code, in eine versehentlich committete .env oder in eine Config-Datei, die jeder User auf der Maschine lesen kann. Sie gehören in eine EnvironmentFile, die nur root lesen kann:

sudo mkdir -p /etc/trading-bot
sudo touch /etc/trading-bot/env
sudo chown root:root /etc/trading-bot/env
sudo chmod 600 /etc/trading-bot/env
EXCHANGE_API_KEY=your-key-here
EXCHANGE_API_SECRET=your-secret-here

This works even though the service runs as the unprivileged botuser: systemd, running as root, reads EnvironmentFile before dropping privileges to start your process, and hands the resulting variables to the already-running process. The file itself never needs to be readable by botuser, so chmod 600 owned by root is the correct, final permission — not a temporary one you loosen later because something "couldn't read it."Das funktioniert, obwohl der Service als der unprivilegierte botuser läuft: systemd liest, während es als root läuft, die EnvironmentFile, bevor es die Rechte fallen lässt, um Ihren Prozess zu starten, und übergibt die resultierenden Variablen an den bereits laufenden Prozess. Die Datei selbst muss für botuser nie lesbar sein, daher ist chmod 600 im Besitz von root die korrekte, endgültige Berechtigung — keine vorläufige, die Sie später lockern, weil irgendetwas sie „nicht lesen konnte“.

Add the file's path to .gitignore before you write anything into it, and check with git status that it never shows up as untracked or staged. A key that reaches a private repo is still a key that reached a repo; rotate it if you're ever unsure.Tragen Sie den Pfad der Datei in die .gitignore ein, bevor Sie irgendetwas hineinschreiben, und prüfen Sie mit git status, dass sie nie als untracked oder staged auftaucht. Ein Key, der in einem privaten Repo landet, ist trotzdem ein Key, der in einem Repo gelandet ist; rotieren Sie ihn, wenn Sie sich jemals unsicher sind.

Now that /etc/trading-bot/env exists, start the service you enabled in Step 2:Jetzt, wo /etc/trading-bot/env existiert, starten Sie den Service, den Sie in Schritt 2 aktiviert haben:

sudo systemctl start trading-bot.service
sudo systemctl status trading-bot.service

Step 4: clock sync with chronySchritt 4: Zeitsynchronisation mit chrony

Most exchange APIs sign requests with a timestamp and reject anything outside a tolerance window, often a few seconds. A drifted VPS clock gets -1021-style "timestamp outside recvWindow" errors on every signed call — it looks exactly like a broken bot and is actually a broken clock.Die meisten Börsen-APIs signieren Requests mit einem Timestamp und lehnen alles außerhalb eines Toleranzfensters ab, oft nur ein paar Sekunden. Eine VPS-Uhr, die driftet, bekommt bei jedem signierten Aufruf Fehler im Stil von -1021, „timestamp outside recvWindow“ — das sieht exakt wie ein kaputter Bot aus, ist aber tatsächlich eine kaputte Uhr.

Ubuntu 24.04 ships systemd-timesyncd by default, which is fine for most things but coarser than you want here. Chrony is the better fit for a machine that needs a tight, actively-monitored offset:Ubuntu 24.04 liefert standardmäßig systemd-timesyncd mit, was für die meisten Zwecke in Ordnung, aber gröber ist, als Sie hier wollen. Chrony passt besser zu einer Maschine, die einen engen, aktiv überwachten Offset braucht:

sudo apt update
sudo apt install -y chrony
sudo systemctl disable --now systemd-timesyncd
sudo systemctl enable --now chrony

Confirm it's actually tracking, not just running:Bestätigen Sie, dass es tatsächlich trackt, nicht nur läuft:

chronyc tracking
chronyc sources -v

chronyc tracking should show a System time offset in the low milliseconds within a minute or two of starting. If it stays wide, check outbound UDP 123 isn't blocked by your firewall rules. The chrony documentation covers tuning makestep and source selection if the defaults don't converge fast enough.chronyc tracking sollte innerhalb von ein, zwei Minuten nach dem Start einen System time-Offset im niedrigen Millisekundenbereich zeigen. Bleibt er weit daneben, prüfen Sie, ob ausgehendes UDP 123 nicht von Ihren Firewall-Regeln blockiert wird. Die chrony-Dokumentation beschreibt, wie Sie makestep und die Source-Auswahl tunen, falls die Standardwerte nicht schnell genug konvergieren.

Step 5: structured logging you can actually grep at 3amSchritt 5: strukturiertes Logging, das Sie um 3 Uhr nachts wirklich grep-en können

Plain print() statements are fine for development and useless at 3am when you need the one line that explains why an order didn't go through. Log as JSON, one object per line, and let journald capture stdout — no separate log file needed:Simple print()-Anweisungen sind für die Entwicklung in Ordnung und um 3 Uhr nachts nutzlos, wenn Sie genau die eine Zeile brauchen, die erklärt, warum eine Order nicht durchging. Loggen Sie als JSON, ein Objekt pro Zeile, und lassen Sie journald stdout mitschneiden — keine separate Log-Datei nötig:

import json
import logging
import sys
import time


class JsonFormatter(logging.Formatter):
    def format(self, record):
        payload = {
            "ts": time.strftime("%Y-%m-%dT%H:%M:%SZ", time.gmtime(record.created)),
            "level": record.levelname,
            "logger": record.name,
            "msg": record.getMessage(),
        }
        if record.exc_info:
            payload["exc"] = self.formatException(record.exc_info)
        return json.dumps(payload)


handler = logging.StreamHandler(sys.stdout)
handler.setFormatter(JsonFormatter())
logging.basicConfig(level=logging.INFO, handlers=[handler])

Because systemd already timestamps everything it captures, ask journalctl for the raw JSON without its own prefix when you want to pipe it somewhere:Weil systemd ohnehin schon alles mit einem Zeitstempel versieht, was es mitschneidet, fragen Sie journalctl nach dem rohen JSON ohne eigenes Präfix, wenn Sie es irgendwohin pipen wollen:

journalctl -u trading-bot.service -o cat -f

journalctl rotates and caps its own storage by default, so you're not manually managing log files. If you add a second destination — a file, a shipper off-box — cap its size explicitly; an unbounded log file is a slow, quiet way to run out of disk.journalctl rotiert und deckelt seinen eigenen Speicher standardmäßig, sodass Sie keine Log-Dateien von Hand verwalten. Fügen Sie ein zweites Ziel hinzu — eine Datei, einen Shipper außerhalb der Maschine —, deckeln Sie dessen Größe explizit; eine unbegrenzte Log-Datei ist eine langsame, leise Art, die Festplatte volllaufen zu lassen.

Step 6: a heartbeat so a dead bot doesn't stay deadSchritt 6: ein Heartbeat, damit ein toter Bot nicht tot bleibt

systemctl status tells you the process is running, not that it's doing anything useful — a bot can be alive, connected, and stuck in a loop that stopped placing orders hours ago, and Restart=on-failure never fires because nothing crashed.systemctl status sagt Ihnen, dass der Prozess läuft, nicht, dass er etwas Sinnvolles tut — ein Bot kann am Leben, verbunden und in einer Schleife gefangen sein, die schon vor Stunden aufgehört hat, Orders zu platzieren, und Restart=on-failure greift nie, weil nichts gecrasht ist.

A dead man's switch fixes this, and it's a natural fit for an outbound-only bot: at the end of every successful loop, ping a monitoring URL.Ein Totmannschalter behebt das, und er passt natürlich zu einem Bot, der nur ausgehend kommuniziert: Am Ende jeder erfolgreichen Schleife pingen Sie eine Monitoring-URL an.

import urllib.request

def send_heartbeat(url: str) -> None:
    try:
        urllib.request.urlopen(url, timeout=5)
    except Exception:
        pass  # a missed heartbeat should never crash the bot

Call send_heartbeat() once per loop, after the real work succeeds, not before it. Pair it with a service that expects a ping on a schedule and pages you when one doesn't arrive — healthchecks.io is the standard example, and it's open source if you'd rather run it yourself. The mechanism matters more than the service: silence is the alert, which is exactly what catches a bot that's technically running but has quietly stopped doing anything.Ruf send_heartbeat() einmal pro Schleife auf, nachdem die eigentliche Arbeit erfolgreich war, nicht davor. Kombinieren Sie es mit einem Dienst, der einen Ping nach Zeitplan erwartet und Sie alarmiert, wenn keiner ankommt — healthchecks.io ist das Standardbeispiel, und es ist Open Source, falls Sie es lieber selbst betreiben wollen. Der Mechanismus zählt mehr als der Dienst: Stille ist der Alarm, und genau das erwischt einen Bot, der technisch läuft, aber still aufgehört hat, irgendetwas zu tun.

Step 7: test the kill switch before you need itSchritt 7: testen Sie den Kill-Switch, bevor Sie ihn brauchen

Every bot needs a way to stop trading immediately, without SSH access being the only lever. The simplest version is a file the bot checks each loop:Jeder Bot braucht eine Möglichkeit, sofort mit dem Handeln aufzuhören, ohne dass SSH-Zugriff der einzige Hebel ist. Die einfachste Version ist eine Datei, die der Bot bei jeder Schleife prüft:

from pathlib import Path

HALT_FILE = Path("/etc/trading-bot/HALT")

def should_halt() -> bool:
    return HALT_FILE.exists()

When should_halt() is true, the bot should cancel open orders it's responsible for, stop placing new ones, log that it halted and why, and exit cleanly with status 0. That last detail is why Restart=on-failure from Step 2 matters: a clean exit is not a failure, so systemd leaves the service stopped instead of bringing it straight back up mid-halt. With Restart=always the kill switch would look like it worked for about five seconds.Ist should_halt() wahr, sollte der Bot die offenen Orders, für die er verantwortlich ist, stornieren, keine neuen mehr platzieren, protokollieren, dass und warum er angehalten hat, und sich sauber mit Status 0 beenden. Genau dieses Detail ist der Grund, warum Restart=on-failure aus Schritt 2 wichtig ist: Ein sauberer Exit ist kein Fehler, also lässt systemd den Service gestoppt, statt ihn mitten im Halt sofort wieder hochzufahren. Mit Restart=always würde der Kill-Switch etwa fünf Sekunden lang so aussehen, als hätte er funktioniert.

Test this on a schedule, not just once after you write it: sudo touch /etc/trading-bot/HALT, watch the bot log its halt and exit, confirm with systemctl status that it's inactive and staying that way, then remove the file and start it again. A kill switch you've never triggered is a theory, not a control. Do this after every deploy that touches the shutdown path — that code is the least exercised by normal operation.Testen Sie das regelmäßig, nicht nur einmal, nachdem Sie es geschrieben haben: sudo touch /etc/trading-bot/HALT, beobachten Sie, wie der Bot seinen Halt protokolliert und sich beendet, bestätigen Sie mit systemctl status, dass er inaktiv ist und bleibt, entfernen Sie dann die Datei und starten Sie ihn wieder. Ein Kill-Switch, den Sie nie ausgelöst haben, ist eine Theorie, keine Kontrolle. Machen Sie das nach jedem Deploy, das den Shutdown-Pfad berührt — dieser Code wird im Normalbetrieb am seltensten durchlaufen.

Back up /etc/trading-bot and the bot's own data directory the same way you'd back up anything else that would hurt to lose — back up your VPS covers what that involves on our machines. A kill switch and a key file are both small, and both are exactly what people forget when "backup" means only the code in git.Sichern Sie /etc/trading-bot und das eigene Datenverzeichnis des Bots genauso, wie Sie alles andere sichern, dessen Verlust wehtun würde — Backup Ihres VPS beschreibt, was das auf unseren Maschinen bedeutet. Ein Kill-Switch und eine Key-Datei sind beide klein, und genau die vergisst man, wenn „Backup“ nur den Code in Git meint.

On overnight.hostBei overnight.host

Full disclosure: this is what we sell. A 1 GiB Starter runs a single Python bot process comfortably around the clock; move up a tier once you're running several bots at once, logging heavily, or keeping a local database of fills.Zur vollen Transparenz: Das ist, was wir verkaufen. Ein 1-GiB-Starter betreibt einen einzelnen Python-Bot-Prozess bequem rund um die Uhr; steigen Sie eine Stufe höher, sobald Sie mehrere Bots gleichzeitig laufen lassen, stark loggen oder eine lokale Datenbank mit Fills führen.

Linux KVM VPS — EUR 4.99 to EUR 59.99 a month, on our own single-tenant bare metal in Dallas, TX and Charlotte, NC. US locations (Dallas, TX and Charlotte, NC) are available; VPS plans can be ordered. Full hardware virtualisation (KVM), your own kernel, full root. Six tiers, vps-starter to vps-ultra. Starter is 1 vCPU, 1 GiB RAM, 25 GB disk.Linux-KVM-VPS — 4,99 bis 59,99 EUR im Monat, auf unserer eigenen Single-Tenant-Bare-Metal-Hardware in Dallas, TX und Charlotte, NC. US-Standorte (Dallas, TX und Charlotte, NC) sind verfügbar; VPS-Tarife können bestellt werden. Vollständige Hardware-Virtualisierung (KVM), eigener Kernel, volles Root. Sechs Tarife, vps-starter bis vps-ultra. Starter hat 1 vCPU, 1 GiB RAM, 25 GB Speicher.

You order in the shop, pay by card (Stripe) or SEPA bank transfer, and your login details are e-mailed to you once the service is set up. Support is e-mail, run by one person, with no guaranteed response time. All prices are final totals under the German small-business rule (§19 UStG); no VAT is added or shown.Sie bestellen im Shop, zahlen per Karte (Stripe) oder SEPA-Überweisung, und Ihre Zugangsdaten werden Ihnen per E-Mail zugeschickt, sobald der Dienst eingerichtet ist. Support läuft per E-Mail, von einer einzelnen Person betrieben, ohne garantierte Reaktionszeit. Alle Preise sind Endpreise. Gemäß § 19 UStG wird keine Umsatzsteuer ausgewiesen.

Order vps-starter → · Linux KVM VPS overviewvps-starter bestellen → · Übersicht Linux-KVM-VPS

Written by the person who runs overnight.host: a small, honest hosting company on dedicated bare metal — Linux VPS, game servers, web hosting. Live status at up.overnight.host.Geschrieben von der Person, die overnight.host betreibt: ein kleines, ehrliches Hosting-Unternehmen auf dedizierter Bare-Metal-Hardware — Linux-VPS, Gameserver, Webhosting. Live-Status unter up.overnight.host.

Technical guidance is informational. Plans, specifications and final prices are listed in the shop. Managed automation and one-click app plans can be ordered directly and are provisioned automatically after payment. US locations (Dallas, TX and Charlotte, NC) are available for VPS, game server, voice and web hosting plans. Custom configurations are still arranged by e-mail.Technische Hinweise dienen der Information. Pläne, Spezifikationen und Endpreise stehen im Shop. Managed-Automation- und One-Click-App-Pläne können direkt bestellt werden und werden nach der Zahlung automatisch bereitgestellt. US-Standorte (Dallas, TX und Charlotte, NC) sind für VPS-, Gameserver-, Voice- und Webhosting-Pläne wieder bestellbar. Sonderkonfigurationen werden weiterhin per E-Mail vereinbart.

FAQFAQ

How much RAM does a trading bot actually need?Wie viel RAM braucht ein Trading-Bot wirklich?

Comfortably under 300 MB for a single bot holding one exchange connection and a modest amount of in-memory state. A 1 GiB VPS covers that with room for the OS and chrony; multiple bots or a growing local database is what pushes you to size up, not the baseline footprint.Deutlich unter 300 MB für einen einzelnen Bot mit einer Börsenverbindung und einer moderaten Menge an Zustand im Speicher. Ein 1-GiB-VPS deckt das mit Platz für das Betriebssystem und chrony ab; mehrere Bots oder eine wachsende lokale Datenbank sind es, die Sie zum Hochskalieren treiben, nicht der Grund-Fußabdruck.

Does NAT IPv4 matter for a trading bot?Spielt NAT-IPv4 für einen Trading-Bot eine Rolle?

No, as long as the bot only makes outbound calls to the exchange's REST and websocket endpoints, which is how virtually every exchange API works. NAT and forwarded ports only matter for services that accept inbound connections, and a trading bot doesn't.Nein, solange der Bot nur ausgehende Aufrufe an die REST- und Websocket-Endpunkte der Börse macht, was so gut wie jede Börsen-API tut. NAT und weitergeleitete Ports spielen nur für Dienste eine Rolle, die eingehende Verbindungen annehmen, und das tut ein Trading-Bot nicht.

Why use chrony instead of the default time sync?Warum chrony statt der Standard-Zeitsynchronisation nutzen?

systemd-timesyncd is fine for general use, but chrony tracks and corrects drift more tightly and gives you chronyc tracking to verify the offset. Exchanges that sign requests with a timestamp and a tolerance window reject calls from a clock that's drifted, and that failure looks like a bot bug until you check the clock.systemd-timesyncd ist für den allgemeinen Gebrauch in Ordnung, aber chrony verfolgt und korrigiert Drift enger und gibt Ihnen mit chronyc tracking die Möglichkeit, den Offset zu prüfen. Börsen, die Requests mit einem Timestamp und einem Toleranzfenster signieren, lehnen Aufrufe von einer Uhr ab, die gedriftet ist, und dieser Fehler sieht wie ein Bot-Bug aus, bis Sie die Uhr prüfen.

Why did my kill switch stop working after I changed the restart policy?Warum funktioniert mein Kill-Switch nicht mehr, nachdem ich die Restart-Policy geändert habe?

Almost always because the unit is set to Restart=always instead of Restart=on-failure. Restart=always restarts on any exit, including a clean, deliberate one, so a kill switch that exits with status 0 gets undone within seconds. Restart=on-failure only restarts on a non-zero exit: crashes recover on their own, deliberate halts stay halted.Fast immer, weil die Unit auf Restart=always statt auf Restart=on-failure gesetzt ist. Restart=always startet bei jedem Exit neu, auch bei einem sauberen, bewussten Exit, sodass ein Kill-Switch, der sich mit Status 0 beendet, innerhalb von Sekunden rückgängig gemacht wird. Restart=on-failure startet nur bei einem Exit ungleich null neu: Crashes erholen sich von selbst, bewusste Halts bleiben angehalten.

Is this guide going to tell me what strategy to run?Sagt mir diese Anleitung, welche Strategie ich fahren soll?

No. This is entirely about keeping a bot you've already built running reliably and safely on a server — restart behaviour, credentials, clock sync, logging, and a kill switch. What the bot decides to trade, and whether it should, is a decision for you to make with your own risk tolerance, not something to take from a hosting guide.Nein. Hier geht es ausschließlich darum, einen Bot, den Sie bereits gebaut haben, zuverlässig und sicher auf einem Server am Laufen zu halten — Restart-Verhalten, Credentials, Zeitsynchronisation, Logging und ein Kill-Switch. Was der Bot handelt und ob er das tun sollte, ist eine Entscheidung, die Sie mit Ihrer eigenen Risikobereitschaft treffen, nicht etwas, das Sie aus einer Hosting-Anleitung übernehmen.

Ready to order?Bereit zu bestellen?

Prices are final totals; no VAT is shown (§19 UStG). Need something the shop does not list? Email us for a written offer.Alle Preise sind Endpreise ohne ausgewiesene USt. (§19 UStG). Sie brauchen etwas, das nicht im Shop steht? Schreiben Sie uns für ein schriftliches Angebot.

US locations available: Dallas, TX and Charlotte, NC for VPS and game servers. Order a VPS → · Order a game server → · Web hosting →
Also live from Germany (EU):
US-Standorte verfügbar: Dallas, TX und Charlotte, NC für VPS und Gameserver. VPS bestellen → · Gameserver bestellen → · Webhosting →
Ebenfalls verfügbar aus Deutschland (EU):

One-click apps, each isolated with its own hostname: Uptime Kuma, Vaultwarden, Gitea, Nextcloud, Ghost, n8n (waitlist) · Managed automation · Managed setupOne-Click-Apps, jeweils isoliert mit eigenem Hostnamen: Uptime Kuma, Vaultwarden, Gitea, Nextcloud, Ghost, n8n (Warteliste) · Managed Automation · Managed Setup

Order now →Jetzt bestellen → Request a custom configIndividuelle Konfiguration anfragen