---
title: "Mehrere WordPress-Websites auf einem Server getrennt betreiben und gemeinsam pflegen"
date: 2026-09-30T22:43:52+02:00
modified: 2026-10-03T07:09:22+02:00
category: wordpress
type: how_to
author: Marcel Schönfelder
canonical: https://s-edv.com/anleitungen/wordpress-mehrere-websites-ein-server-vhost-wp-cli-alias
keywords:
  - WordPress
  - WP-CLI
  - Apache
  - Server
  - Wartung
reading_time: 10
---

# Mehrere WordPress-Websites auf einem Server getrennt betreiben und gemeinsam pflegen

Viele kleine Unternehmen betreiben mehr als eine WordPress-Website, etwa Firmenseite, Onlineshop und eine Projektseite. Liegen alle auf demselben Server, spart das Kosten und Verwaltungsaufwand. Eine kompromittierte Website darf aber nicht die anderen mitreißen, und jede Installation will aktualisiert und gesichert werden. Diese Anleitung zeigt, wie Sie mehrere eigenständige WordPress-Installationen auf einem Linux-Server mit Apache sauber voneinander trennen und anschließend mit WP-CLI-Aliasen gemeinsam pflegen, ohne sich auf jeder Website einzeln anmelden zu müssen.

**Kurzfassung:** Jede Website bekommt ein eigenes Verzeichnis unter `/var/www`, eine eigene Datenbank mit eigenem Datenbankbenutzer und einen eigenen Apache-VirtualHost. Mit `open_basedir` begrenzen Sie, welche Dateien PHP je Website lesen darf. Installiert wird per WP-CLI mit `wp core download`, `wp config create` und `wp core install`. Anschließend tragen Sie alle Websites als Aliase in `~/.wp-cli/config.yml` ein und fassen sie zu einer Gruppe zusammen. Ein Befehl wie `wp @alle plugin list --update=available` zeigt dann ausstehende Updates aller Websites auf einmal.

## Voraussetzungen

- [ ] **Server:** ein Linux-Server (Debian oder Ubuntu) mit Apache, PHP und MariaDB oder MySQL. Für zwei bis drei kleine Firmenwebsites mit wenig Traffic genügen 2 CPU-Kerne und 4 GB RAM als Ausgangspunkt, x86-64 oder ARM. Wie Sie prüfen, ob die Ressourcen reichen, lesen Sie in [WordPress-Hosting-Ressourcen prüfen](https://s-edv.com/anleitungen/wordpress-hosting-ressourcen-php-worker-memory-limit-pruefen).
- [ ] **WordPress und PHP:** Die Anleitung nutzt WordPress 7.1.2; WordPress empfiehlt PHP 7.4 als Mindestversion, sinnvoll ist eine aktuelle Version wie PHP 8.4.
- [ ] **Zugriff:** SSH mit sudo-Rechten, Zugang zur Datenbank als Root oder mit einem Benutzer, der Datenbanken und Benutzer anlegen darf, sowie WP-CLI auf dem Server.
- [ ] **Rolle:** Für jede Website ein Konto mit der Rolle Administrator.
- [ ] **DNS:** Die Domains der Websites zeigen per A- bzw. AAAA-Eintrag auf die IP-Adresse des Servers.
- [ ] **Backup:** Wenn bereits Websites auf dem Server laufen, sichern Sie Dateien und Datenbanken, bevor Sie die Apache-Konfiguration ändern.

## Schritt 1: Getrennte Installationen oder Multisite entscheiden

WordPress kennt zwei Wege, mehrere Websites zu betreiben. Bei einer **Multisite** teilen sich alle Websites eine Installation, eine Datenbank, dieselben Plugins und dieselben Updates. Die Entscheidung dafür beschreibt die Anleitung [WordPress-Multisite: Wann es sich lohnt und wie Sie es einrichten](https://s-edv.com/anleitungen/wordpress-multisite-netzwerk-einrichten-entscheidung).

Diese Anleitung behandelt den anderen Weg: **getrennte Installationen**. Jede Website hat eigene Dateien, eine eigene Datenbank und eigene Plugins. Das kostet etwas mehr Pflege, hat aber klare Vorteile. Ein Shop und eine schlichte Firmenseite brauchen unterschiedliche Plugins, eine Website lässt sich einzeln umziehen, und ein fehlerhaftes Update betrifft nur eine Website. Für Unternehmen mit wenigen, unterschiedlichen Websites ist das meist die robustere Wahl.

Legen Sie vorab ein Verzeichnis je Website mit sprechendem Namen fest:

```plaintext
/var/www/firma-a      Firmenwebsite
/var/www/kunde-b      zweite Website
/var/www/shop-c       Onlineshop
```

> **Prüfen:** Sie haben für jede Website einen Kurznamen, ein Verzeichnis und die zugehörige Domain notiert. Dieselben Kurznamen verwenden Sie in den folgenden Schritten für Datenbank, VirtualHost und Alias.

## Schritt 2: Eigene Datenbank und eigenen Datenbankbenutzer anlegen

Der wichtigste Trennschritt passiert in der Datenbank. Nutzen alle Websites denselben Datenbankbenutzer, kann ein Angreifer mit den Zugangsdaten aus einer `wp-config.php` sämtliche Datenbanken lesen und verändern. Legen Sie deshalb je Website eine eigene Datenbank und einen Benutzer an, der nur diese eine Datenbank sieht:

Datei: `wp-config.php`

```sql
CREATE DATABASE wp_kundeb CHARACTER SET utf8mb4 COLLATE utf8mb4_unicode_ci;
CREATE USER 'wp_kundeb'@'localhost' IDENTIFIED BY 'LANGES-ZUFALLSPASSWORT';
GRANT ALL PRIVILEGES ON wp_kundeb.* TO 'wp_kundeb'@'localhost';
```

Führen Sie die Befehle auf dem Server mit `sudo mariadb` aus. Ein Passwort erzeugt zum Beispiel `openssl rand -base64 24`.

> **Prüfen:** Melden Sie sich als neuer Benutzer an und lassen Sie sich die Datenbanken anzeigen. Es dürfen nur `information_schema` und die eigene Datenbank erscheinen. Ein Zugriff auf eine fremde Datenbank endet mit einer Meldung wie `SELECT command denied to user 'wp_kundeb'@'localhost' for table ...`. Genau diese Meldung ist hier das gewünschte Ergebnis.

## Schritt 3: WordPress per WP-CLI installieren

Mit WP-CLI installieren Sie WordPress in wenigen Befehlen und ohne den Browser-Installer, der bis zum Abschluss offen im Netz steht. Arbeiten Sie dabei nicht als root, sondern als der Benutzer, dem die Dateien gehören. Unter Debian und Ubuntu mit Apache und mod_php ist das `www-data`:

```bash
sudo mkdir -p /var/www/kunde-b
sudo chown www-data:www-data /var/www/kunde-b
cd /var/www/kunde-b
sudo -u www-data wp core download --locale=de_DE
sudo -u www-data wp config create --dbname=wp_kundeb --dbuser=wp_kundeb \
  --dbpass='LANGES-ZUFALLSPASSWORT' --dbhost=localhost --dbprefix=kb_
sudo -u www-data wp core install --url=https://kunde-b.example --title="Kunde B" \
  --admin_user=kb-admin --admin_email=webmaster@kunde-b.example --prompt=admin_password
```

`wp config create` erzeugt eine `wp-config.php` mit frischen Sicherheitsschlüsseln. Der eigene Tabellenpräfix `kb_` ist bei getrennten Datenbanken nicht zwingend, macht Dumps aber eindeutig zuordenbar. `--prompt=admin_password` fragt das Passwort interaktiv ab, damit es nicht in der Shell-Historie landet.

> **Prüfen:** `sudo -u www-data wp core version --extra` im Verzeichnis der Website zeigt die WordPress-Version und das Sprachpaket `de_DE`. Die Datei `wp-config.php` gehört `www-data`; wie Sie die Rechte danach enger setzen, beschreibt [Dateirechte in WordPress richtig setzen](https://s-edv.com/anleitungen/wordpress-dateirechte-richtig-setzen-wp-config-chmod-chown).

## Schritt 4: Apache-VirtualHost je Website anlegen

Apache entscheidet anhand des angefragten Hostnamens, welche Website ausgeliefert wird. Dafür bekommt jede Website eine eigene Datei unter `/etc/apache2/sites-available`:

```plaintext
<VirtualHost *:80>
    ServerName kunde-b.example
    ServerAlias www.kunde-b.example
    DocumentRoot /var/www/kunde-b
    <Directory /var/www/kunde-b>
        AllowOverride All
        Require all granted
    </Directory>
    php_admin_value open_basedir /var/www/kunde-b/:/tmp/
    ErrorLog ${APACHE_LOG_DIR}/kunde-b-error.log
    CustomLog ${APACHE_LOG_DIR}/kunde-b-access.log combined
</VirtualHost>
```

`AllowOverride All` brauchen Sie, damit die `.htaccess` von WordPress für Permalinks greift. Die Zeile mit `open_basedir` ist der eigentliche Schutz zwischen den Websites: PHP darf für diese Website nur Dateien im eigenen Verzeichnis und in `/tmp` öffnen. Ein Schadskript in `kunde-b` kann dann nicht einfach die `wp-config.php` von `firma-a` auslesen. `php_admin_value` funktioniert nur mit mod_php und lässt sich über `.htaccess` nicht wieder aufheben.

Aktivieren Sie die Website, prüfen Sie die Syntax und laden Sie Apache neu:

```bash
$ sudo a2ensite kunde-b
$ sudo apache2ctl configtest
$ sudo systemctl reload apache2
```

Ein ehrlicher Hinweis zur Grenze dieser Trennung: Mit mod_php laufen alle Websites unter demselben Systembenutzer `www-data`. `open_basedir` schränkt PHP ein, trennt aber nicht die Dateirechte auf Betriebssystemebene. Stärker ist PHP-FPM mit einem eigenen Pool je Website, der unter einem eigenen Linux-Benutzer läuft (Direktiven `user` und `group` in der Pool-Konfiguration, `open_basedir` dort über `php_admin_value[open_basedir]`). Wie PHP-FPM mit Nginx eingerichtet wird, zeigt [WordPress auf Nginx mit PHP-FPM konfigurieren](https://s-edv.com/anleitungen/wordpress-nginx-php-fpm-konfigurieren-server-block). Für HTTPS richten Sie danach je Domain ein Zertifikat ein, etwa mit Certbot.

> **Prüfen:** `sudo apache2ctl -S` listet für Port 80 einen Eintrag `namevhost kunde-b.example` mit der richtigen Konfigurationsdatei. `curl -sI -H 'Host: kunde-b.example' http://localhost/` liefert `HTTP/1.1 200 OK`. Legen Sie zum Test von `open_basedir` kurz eine PHP-Datei an, die eine Datei der anderen Website liest; sie muss mit `Operation not permitted` scheitern. Löschen Sie die Testdatei danach sofort.

## Schritt 5: WP-CLI-Aliase für alle Websites einrichten

Bisher müssen Sie für jeden Befehl in das jeweilige Verzeichnis wechseln. Aliase ersparen das. Sie werden laut WP-CLI-Handbuch in der globalen Datei `~/.wp-cli/config.yml` des Benutzers oder in einer `wp-cli.yml` im Projekt eingetragen. Eine Liste von Aliasen bildet eine Alias-Gruppe:

Datei: `wp-cli.yml`

```yaml
@firma-a:
  path: /var/www/firma-a
@kunde-b:
  path: /var/www/kunde-b
@shop-c:
  path: /var/www/shop-c
@alle:
  - @firma-a
  - @kunde-b
  - @shop-c
```

Die Datei gilt nur für ihren Benutzer. Arbeiten Sie mit `sudo -u www-data`, muss die Konfiguration für diesen Benutzer auffindbar sein, sonst meldet WP-CLI `Error: Alias '@alle' not found.` Die Umgebungsvariable `WP_CLI_CONFIG_PATH` zeigt WP-CLI eine Konfigurationsdatei an anderer Stelle. Liegen Websites auf verschiedenen Servern, kann ein Alias statt `path` auch eine SSH-Verbindung enthalten, zum Beispiel `ssh: deploy@server2.example/var/www/shop-c`. Dann muss WP-CLI auch auf dem entfernten Server installiert sein.

> **Prüfen:** `wp cli alias list` zeigt Ihre Aliase und die Gruppe. `wp @alle option get siteurl` gibt für jede Website unter ihrem Alias die richtige Adresse aus:
>
> ```plaintext
> @firma-a
> https://firma-a.example
> @kunde-b
> https://kunde-b.example
> ```

## Schritt 6: Updates, Prüfungen und Backups für alle Websites

Jetzt zahlt sich die Vorarbeit aus. Mit einem Befehl sehen Sie, wo Updates ausstehen:

```bash
$ wp @alle core check-update
$ wp @alle plugin list --update=available --fields=name,version,update_version
$ wp @alle theme list --update=available
```

Die Ausgabe ist nach Alias gruppiert. Spielen Sie Updates trotzdem Website für Website ein und nicht blind mit `wp @alle plugin update --all`. Ein Update, das auf der Firmenseite problemlos läuft, kann im Shop mit einem anderen Plugin kollidieren. `--dry-run` zeigt vorher, was aktualisiert würde. Das genaue Vorgehen mit Backup und Kontrolle beschreibt [WordPress-Updates mit WP-CLI](https://s-edv.com/anleitungen/wordpress-updates-wp-cli-core-plugins-themes).

Weitere Routineprüfungen lassen sich ebenso für alle Websites ausführen:

```bash
$ wp @alle core verify-checksums
$ wp @alle user list --role=administrator --fields=user_login,user_email
$ wp @alle db export --add-drop-table
```

`verify-checksums` vergleicht die Core-Dateien mit den offiziellen Prüfsummen und findet veränderte Dateien. Die Administratorliste zeigt vergessene Konten, etwa von ehemaligen Mitarbeitern oder Agenturen. `db export` legt je Website einen Datenbank-Dump an, dessen Dateiname mit dem Datenbanknamen beginnt. Die Dateien landen im aktuellen Arbeitsverzeichnis, nicht im Verzeichnis der Website. Wechseln Sie deshalb vorher in ein Sicherungsverzeichnis außerhalb des Webroots und kopieren Sie die Dumps anschließend auf einen externen Speicher. Ein vollständiges Sicherungsskript mit Dateien und Aufbewahrung zeigt [WordPress-Backup per Cronjob und Shell-Skript](https://s-edv.com/anleitungen/wordpress-backup-server-cronjob-shell-skript).

Spätestens hier wird deutlich, dass mehrere Websites vor allem laufende Arbeit bedeuten: Updates prüfen und einspielen, Backups kontrollieren, Konten aufräumen, und das für jede Website einzeln. Wer diese Aufgaben nicht selbst im Kalender halten möchte, kann sie abgeben: Die [WordPress-Wartung von wordpressupdate.de](https://wordpressupdate.de/?utm_source=s-edv.com&utm_medium=artikel&utm_campaign=113) übernimmt Updates von WordPress, Plugins und Themes mit Kompatibilitätsprüfung, wöchentliche Backups auf externen Speicher mit vier Wochen Aufbewahrung sowie die Einrichtung und Pflege der Firewall.

> **Prüfen:** `wp @alle core verify-checksums` meldet für jede Website `Success: WordPress installation verifies against checksums.`, und nach `db export` liegt je Website eine aktuelle SQL-Datei vor, die Sie an den externen Speicherort verschoben haben.

## Typische Fehler

**`Error: YIKES! It looks like you're running this as root.`**

WP-CLI verweigert die Arbeit als root, weil dann jeder Code der Website volle Rechte am Server hätte. Führen Sie Befehle als Eigentümer der Dateien aus (`sudo -u www-data wp ...`). `--allow-root` umgeht die Sperre, sollte aber die Ausnahme bleiben.

**`Error: Alias '@alle' not found.`**

Die Alias-Datei liegt im Home-Verzeichnis eines anderen Benutzers. Legen Sie sie für den Benutzer an, unter dem Sie WP-CLI ausführen, oder setzen Sie `WP_CLI_CONFIG_PATH`.

**`PHP Fatal error: Allowed memory size of 134217728 bytes exhausted` bei `wp core download`.**

Das Entpacken des WordPress-Archivs braucht auf manchen Systemen mehr als 128 MB. Rufen Sie WP-CLI mit höherem Limit auf, etwa `php -d memory_limit=512M /usr/local/bin/wp core download`, oder erhöhen Sie `memory_limit` in der php.ini für die Kommandozeile.

**`Failed to get current SQL modes. Reason: env: 'mysql': No such file or directory`**

bei `wp db query` oder `wp db export`. Diese Befehle rufen den Datenbank-Client des Systems auf. Installieren Sie das Paket `mariadb-client` bzw. den MySQL-Client.

**Falsche Website erscheint.**

Passt kein `ServerName`, antwortet der erste VirtualHost, meist `000-default.conf`. `apache2ctl -S` zeigt die bekannten Namen.

**Uploads oder Plugin-Installationen scheitern nach dem Setzen von `open_basedir`.**

Prüfen Sie im Fehlerlog der Website, welcher Pfad blockiert wird. Häufig fehlt das temporäre Verzeichnis in der Liste.

## Häufige Fragen

### Wie viele WordPress-Websites verträgt ein Server?

Eine feste Zahl gibt es nicht. Entscheidend sind Besucherzahlen, Caching und gleichzeitige PHP-Prozesse. Beobachten Sie Auslastung und Antwortzeiten nach jeder neuen Website und ziehen Sie eine stark besuchte Website notfalls auf einen eigenen Server um.

### Brauche ich ein Hosting-Panel?

Nicht zwingend. Die Schritte oben kommen mit Bordmitteln aus. Ein Panel nimmt Ihnen VirtualHosts, PHP-Versionen je Website, Zertifikate und getrennte Systembenutzer über eine Oberfläche ab. Beispiele sind [KeyHelp](https://s-edv.com/anleitungen/keyhelp-installieren-absichern-eigener-server) oder das Hestia Control Panel. Das Panel muss dann ebenfalls gepflegt werden.

### Kann ich Aliase auch für Websites bei verschiedenen Hostern nutzen?

Ja, sofern Sie per SSH Zugriff haben und WP-CLI dort verfügbar ist. Tragen Sie beim Alias statt `path` die Option `ssh` mit Benutzer, Host und Pfad ein. Die Gruppe kann lokale und entfernte Aliase mischen.

## Fazit

Mehrere WordPress-Websites auf einem Server sind gut beherrschbar, wenn jede Website eigene Dateien, eine eigene Datenbank mit eigenem Benutzer und einen eigenen VirtualHost bekommt. `open_basedir` erschwert es, dass ein Problem auf eine andere Website übergreift, PHP-FPM mit getrennten Benutzern trennt noch stärker. WP-CLI-Aliase machen aus fünf einzelnen Wartungsrunden eine gemeinsame Übersicht, die eigentliche Sorgfalt beim Einspielen der Updates bleibt aber Ihre Aufgabe. Wenn Ihnen die Zeit dafür fehlt, können Sie Updates und Backups an eine [externe WordPress-Wartung](https://wordpressupdate.de/?utm_source=s-edv.com&utm_medium=fazit&utm_campaign=113) abgeben.

## Weiterführende Anleitungen und Quellen

- [WordPress-Multisite: Wann es sich lohnt und wie Sie es einrichten](https://s-edv.com/anleitungen/wordpress-multisite-netzwerk-einrichten-entscheidung)
- [WordPress-Updates mit WP-CLI einspielen](https://s-edv.com/anleitungen/wordpress-updates-wp-cli-core-plugins-themes)
- [WordPress-Backup per Cronjob und Shell-Skript](https://s-edv.com/anleitungen/wordpress-backup-server-cronjob-shell-skript)
- [WP-CLI-Handbuch: Config (Aliase und Alias-Gruppen)](https://make.wordpress.org/cli/handbook/references/config/)
- [WP-CLI-Handbuch: Running Commands Remotely](https://make.wordpress.org/cli/handbook/guides/running-commands-remotely/)
- [WP-CLI-Befehlsreferenz: wp config create](https://developer.wordpress.org/cli/commands/config/create/)
- [Apache-Dokumentation: Name-based Virtual Hosts](https://httpd.apache.org/docs/2.4/vhosts/name-based.html)
- [PHP-Handbuch: open_basedir](https://www.php.net/manual/de/ini.core.php#ini.open-basedir)
- [PHP-Handbuch: FPM-Konfiguration](https://www.php.net/manual/de/install.fpm.configuration.php)
