Ein Deployment auf den eigenen Server bedeutet, einem Agenten SSH-nahen Zugriff auf eine Maschine zu geben, für die man bezahlt und auf der bereits andere Dinge laufen könnten. Das ist ein anderes Vertrauensniveau als die Veröffentlichung auf einer kostenlosen Subdomain, und die Einrichtung spiegelt das wider — ein paar Felder, einmal ausgefüllt, und danach ist jeder Build nur noch ein Klick. Hier sind die Fragen, die tatsächlich gestellt werden, bevor und nachdem man ein solches Ziel einrichtet.
Was brauche ich, um ein Ziel zu erstellen?
Fünf Dinge, unter Einstellungen → Deploy:
- Ein Name, den man später wiedererkennt — „prod-vps“, „client-hostgator“, was auch immer ein Dropdown-Menü um 23 Uhr übersteht
- Host und Port
- SFTP-Zugangsdaten
- Ein Webroot-Pfad
Keine API-Token, kein CLI, das auf dem Server installiert werden muss, kein Cron-Job, um den man sich kümmern muss. Wenn Ihr Hoster SFTP-Zugang bereitstellt — was praktisch jedes Shared Hosting, jeden VPS und jede verwaltete WordPress-Instanz abdeckt — ist man in etwa zwei Minuten fertig.
Passwort oder Schlüssel?
Schlüssel, falls Ihr Hoster das unterstützt. Passwörter funktionieren einwandfrei, und wir speichern sie kontobezogen, aber ein Schlüssel ist ein Geheimnis weniger, das irgendwo herumliegt — der Unterschied zwischen „einen Schlüssel widerrufen“ und „ein Passwort überall zurücksetzen, wo es zufällig wiederverwendet wurde“, falls später etwas schiefgeht. Viele günstige SFTP-Setups im Shared Hosting bieten ohnehin nur Passwort-Authentifizierung, und das ist auch in Ordnung. Verwenden Sie dieses Passwort nur nicht anderswo wieder.
Wie finde ich den richtigen Webroot-Pfad?
Das ist das Feld, bei dem man sich beim ersten Mal am häufigsten vertut, weil die falsche Antwort trotzdem plausibel aussieht. Es ist nicht Ihr Home-Verzeichnis, es ist nicht /var/www — es ist genau der Ordner, aus dem Ihr Webserver konfiguriert ist, Inhalte auszuliefern.
| Server | Typischer Webroot |
|---|---|
| Apache / cPanel | public_html |
| Nginx | /var/www/mysite/html — oder irgendein Pfad, den ein früherer Entwickler vor drei Jahren aus Gründen benannt hat, an die sich niemand mehr erinnert |
Falls Sie sich nicht sicher sind, legen Sie mit einem beliebigen SFTP-Client eine Wegwerf-Datei test.txt in den Ordner, den Sie für richtig halten, und prüfen Sie dann, ob sie unter yoursite.com/test.txt geladen wird. Liegt man hier falsch, meldet das Deployment trotzdem Erfolg — der Agent schreibt die Dateien brav in den falschen Ordner, und man steht am Ende vor einer Live-Website, die sich nicht verändert hat, und fragt sich warum.
Kann ein Ziel mehr als eine Domain abdecken?
Ja, und genau das spart echte Zeit, sobald man über die erste Website hinaus ist. Ein Ziel besteht aus einem Server und einem Satz Zugangsdaten — es ist nicht an eine einzige Domain gebunden. Unter Domain-Verwaltung verknüpfen Sie jede Domain mit einem Ziel und einem eigenen Webroot-Override. Betreiben Sie drei Websites auf einem VPS mit Nginx-Server-Blocks?
site-a→/var/www/site-asite-b→/var/www/site-bsite-c→/var/www/site-c
Ein Ziel, drei Verknüpfungen. Sie geben nicht dreimal dasselbe SSH-Passwort ein und pflegen nicht drei nahezu identische Ziele, die auseinanderdriften, sobald Sie einen Schlüssel rotieren und eines davon vergessen. Klicken Sie bei einer der drei Domains auf Deploy, weiß das System bereits, welcher Server und welcher Ordner gemeint sind — die Auswahl entfällt beim Deployment.
Was macht der Agent eigentlich, wenn er sich verbindet?
Zuerst schaut er sich um — nur lesend, noch nichts wird geschrieben. Diese Prüfung untersucht:
- Einen leeren Ordner
- Eine frühere Version genau dieses Builds
- Eine alte WordPress-Installation
- Einen „Coming Soon“-Platzhalter, den Ihr Hoster standardmäßig dort abgelegt hat
Das entscheidet über die Strategie. Ein leerer Webroot erhält einen einfachen Upload. Ein Webroot mit vorhandenem Inhalt wird vorsichtiger behandelt, denn bei vielen realen Setups liegen Dinge neben der eigentlichen Website, die nicht verschwinden dürfen:
- A
.well-known-Ordner für die SSL-Validierung - Ein
uploads-Verzeichnis, das niemand in Git aufgenommen hat - A
wp-config.phpdas niemand angefasst haben möchte
Die Aufgabe hier ähnelt eher „herausfinden, was sich geändert hat, und es abgleichen“ als „löschen und ersetzen“.
Bevor auch nur ein einziges Byte überschrieben wird, wird der bestehende Webroot als Version auf Ihrem eigenen Host gesichert. Kein Datenbankeintrag, kein berechneter Diff, von dem man hofft, dass er stimmt — sondern ein tatsächlicher Schnappschuss dessen, was dort lag. Das ist besonders beim allerersten Deployment auf ein Ziel wichtig, denn dieses Deployment landet immer auf irgendetwas, selbst wenn dieses Etwas nichts ist. Leerer Ordner, leerer Schnappschuss. Fünf Jahre alte statische Website, an deren Erstellung sich niemand mehr erinnert — exakt bewahrt, kostenlos, bevor sie angefasst wird. Genau bei diesem ersten Deployment ist man sich am unsichersten, weshalb es dort am meisten zählt.
Wird mein Quellcode oder die gebaute Website hochgeladen?
Immer die gebaute Website. Bei einer statischen Website sind das die generierten Seiten. Bei einem Framework-Build — Next.js, Vite, was auch immer der Website-Typ verlangt — ist es die kompilierte Ausgabe, der dist oder build -Ordner, niemals der Quellcode-Baum. Das halte ich für die richtige Entscheidung, auch wenn man dadurch nicht per SSH einloggen und npm run dev gegen das ausführen kann, was auf dem Server liegt. Den Quellcode hochzuladen würde bedeuten, dass Ihr Produktions-Webroot eine Node-Laufzeitumgebung und ein komplettes Build-Toolchain benötigt, nur um HTML auszuliefern — eine Shared-Hosting-Maschine, die nie dafür gedacht war, eine Build-Pipeline auszuführen, würde genau dazu gemacht, und jedes Deployment würde zu „hoffen, dass der Server genug Speicher hat, um npm install abzuschließen“. Nur kompilierte Ausgabe auszuliefern hält den Webroot genau so, wie ein statischer Dateiserver ihn erwartet. Langweilig. Und langweilig ist genau das, was man um 2 Uhr nachts will, wenn etwas nicht stimmt und man vor diesem Ordner sitzt und herausfinden will, was da eigentlich ausgeliefert wird.
Woher weiß ich, dass ein Deployment tatsächlich funktioniert hat?
Nach dem Upload ruft der Agent die Live-URL auf und prüft, ob sie erreichbar ist — kein 500er, keine leere Seite. Was er dabei findet, sowie alles, was ihm bei der Inspektion aufgefallen ist und wozu er Ihre Rückmeldung möchte („dieser Webroot enthält einen wp-content -Ordner, den ich unangetastet gelassen habe, bitte bestätigen Sie, dass das so gewollt ist“), landet im Chat-Thread des Builds. Das ist das Muster, das sich durch die gesamte Plattform zieht: kein stiller Erfolg, kein stilles Scheitern, das erst als Support-Ticket auftaucht. Der Agent teilt mit, was er gesehen und entschieden hat, im selben Thread, in dem der Build angefordert wurde.
Was steht eigentlich im Versionsverlauf?
Jedes Deployment fügt eine Version hinzu — nicht nur das erste. Der Verlauf zeigt also nicht Ihre Builds auf einer abstrakten Zeitachse, sondern die tatsächliche Abfolge dessen, was von diesem Webroot ausgeliefert wurde, in der richtigen Reihenfolge, beginnend mit dem, was vor Ihrer Ankunft dort lag. Version eins ist immer dieser Zustand vor der Plattform, automatisch erfasst. Darüber müssen Sie sich keine Gedanken machen.
Was stellt „Zurücksetzen“ eigentlich wieder her?
Exakt die vorherige Live-Version — kein erneuter Lauf eines alten Builds, keine Annäherung. Die tatsächlichen Dateien, die zuvor den Traffic bedient haben. Das ist eine deutlich stärkere Garantie als bei den meisten „Rollback“-Funktionen, die ich anderswo genutzt habe und die meist bedeuten „von einem alten Commit neu deployen“ und stillschweigend voraussetzen, dass Ihr Build-Prozess deterministisch ist und sich Ihre Umgebung seither nicht verändert hat. Hier ist ein Rollback die Wiederherstellung eines bekanntermaßen funktionierenden Schnappschusses — deshalb kann man ihn unter Druck bedenkenlos nutzen, ohne darüber nachdenken zu müssen, ob sich das Rollback anders verhält als das, worauf es zurücksetzt.
Und der Moment, in dem man ihn tatsächlich braucht, ist nie ein ruhiger — es heißt dann „der neue Build hat den Checkout kaputtgemacht, und der Traffic läuft gerade live“.
Ein Klick, vorherige Version wiederhergestellt, fertig. Die Überlegungen, warum dies als vollwertige Funktion und nicht als Nebensache behandelt wird, stehen in Iterieren ohne Angst — lesenswert, einmal, bevor man es braucht. Sowohl der Verlauf als auch die Wiederherstellungsfunktion befinden sich auf der Build-Karte und in der eigenen Verlaufsansicht des Ziels.
Sichert das auch meine Datenbank?
Nein, und ich sage das lieber klar, als es jemanden annehmen zu lassen. Der Versionsverlauf auf dem Host deckt ab, was diese Deployment-Pipeline im Webroot abgelegt hat. Wenn Ihre Website eine Datenbank, Nutzer-Uploads oder anderes hat, das sich außerhalb von Deployments verändert, ist das ein völlig separates Thema — „Zurücksetzen“ rührt das nicht an und sollte nicht mit einer Backup-Strategie verwechselt werden, die das tut.



