WordPress absichern (Hardening)
Vorwort
Diese Dokumentation beschreibt den Installationsvorgang von Sicherheitsmechanismen zur Absicherung einer WordPress-Installation.
Bitte vergewissern Sie sich, dass Ihr System über die nötigen Voraussetzungen verfügt, wie in der Infobox beschrieben. Weiterhin sind Grundkenntnisse im Umgang mit Linux erforderlich, da die Vorgehensweise, wie sie hier beschrieben ist, in manchen Teilen abweichen kann. Kein System ist wie das Andere. Die Dokumentation wurde sorgfältig von mir geprüft. Dennoch kann ich keinerlei Haftung für Schäden an Ihrem System oder eine Gewährleistung übernehmen. Bitte verwenden Sie diese Dokumentation auf eigene Gefahr.
Verwendete Software:
Voraussetzungen:
- fertige WordPress-Installation
Weitere, empfohlene Dokumentationen:
Maßnahmen
Auch wenn es sich von selbst erklärt, weise ich ausdrücklich darauf hin, dass eine der wichtigsten Maßnahmen die Verwendung von starken Passwörtern ist!
MySQL-Verbindung über SSL herstellen
Befinden sich die Wordpress-Installation und der MySQL-Server nicht auf der gleichen Maschine, können Übertragungen durch einfaches Mitschneiden des Netzwerkverkehrs abgefangen werden. Die Übertragung sollte daher verschlüsselt stattfinden.
Wichtig: Der MySQL-Server muss SSL unterstützen.
Fügen Sie der Datei wp-config.php
folgendes hinzu:
[...]
/**
* Verwende SSL-Verbindung zu MySQL-Server.
*/
define('MYSQL_CLIENT_FLAGS', MYSQLI_CLIENT_SSL);
[...]
Auslesen von Benutzernamen verhindern
Um den, einer ID zugehörigen, Benutzernamen zu ermitteln, reicht folgender Aufruf:
www.example.com/wordpress/?author=<ID>
Ermittelt also ein Angreifer über den Aufruf
www.example.com/wordpress/?author=1
einen Benutzernamen, kann er sich sehr sicher sein, dass dieser über Administrations-Rechte verfügt.
Das Auslesen über diesen Aufruf kann mit einem entsprechenden Eintrag in einer .htaccess-Datei ganz verhindert werden.
Standard-Benutzer löschen
- Legen Sie also zunächst einen neuen Benutzer an und weisen Sie ihm die Rolle 'Administrator' zu.
- Melden Sie sich mit dem Standard-Benutzer ab und mit dem neuen Benutzer wieder an.
- Löschen Sie anschliessend den Standard-Benutzer (und damit die ID 1).
.htaccess erstellen
Erstellen Sie im Hauptordner der WordPress-Installation (z.B. /var/www/html/wordpress
) eine .htaccess-Datei mit folgendem Inhalt.
Achten Sie darauf, dass Sie den korrekten Pfad angeben:
# Verhindert das Auslesen von Benutzernamen über ?author=<ID> # Auf korrekten Pfad achten! RewriteEngine On RewriteBase / RewriteCond %{QUERY_STRING} .*author=(.+.?) [NC] RewriteRule (.*) /wordpress/?author= [NC,L,R=301]
Administrations-Bereich absichern
wp-login.php
gelangt man auf die Login-Seite der WordPress-Administrations-Oberfläche. Daher ist diese Datei auch das erste Ziel für Brute-Force-Angriffe.Ein weiteres Ziel ist die Datei wp-config.php
. Diese Datei enthält sensible Daten, wie z.B. Zugangsdaten zur Datenbank. Auch wenn diese Datei nur bei wirklich grober Fehlkonfiguration ausgelesen werden kann, sollte sie vor unberechtigtem Zugriff geschützt werden (Murphys Gesetz: "Alles, was schiefgehen kann, wird auch schiefgehen").
Wir sichern den Zugang zum Administrations-Bereich mit einer .htaccess-Datei.
Im ersten Schritt erstellen wir die Datei .htpasswd
. Diese Datei enthält den (oder mehrere) Benutzernamen und den MD5-Hashwert des dazugehörigen Passworts. Daher sollte sie ausserhalb des Webserver-Verzeichnisses liegen.
Im zweiten Schritt erstellen wir im Hauptordner der WordPress-Installation, z.B. /var/www/html/wordpress
, die Datei .htaccess
.
Sie enthält im Wesentlichen folgende Informationen:
AuthType Basic
Methode, die für die Authentifizierung verwendet wird.AuthName
Titel des Login-Fensters.AuthUserFile
Ablageort der .htpasswd-Datei.require valid-user
In der .htpasswd aufgeführte Benutzer, denen nach erfolgreicher Eingabe von Benutzername und Passwort Zugriff gewährt wird.
('valid-user' = Alle, in der .httpasswd aufgeführten.)
.htpasswd erstellen
Im ersten Schritt erstellen wir die Datei .htpasswd
im Ordner /etc
und legen einen Benutzer an:
# htpasswd -c /etc/.htpasswd <BENUTZERNAME>
New password: ****************
Re-type new password: ****************
Adding password for user <BENUTZERNAME>
.htaccess erstellen
Im zweiten Schritt erstellen wir die Datei .htaccess
im Hauptordner der WordPress-Installation, z.B. /var/www/html/wordpress
:
# nano /var/www/html/wordpress/.htaccess
# Fordert eine zusätzliche Eingabe von Benutzername/Kennwort ein (entsprechend .htpasswd) <Files wp-login.php> AuthType Basic AuthName "Zugriff verweigert - Bitte Benutzernamen und Passwort eingeben" AuthUserFile /etc/.htpasswd require valid-user </Files> # Verweigert Zugriff auf sensible Dateien <FilesMatch "(\.htaccess|\.htpasswd|wp-config\.php|liesmich\.html|readme\.html|license\.txt)"> order deny,allow deny from all </FilesMatch> # Verhindert das Auslesen von Benutzernamen über ?author=<ID> # Auf korrekten Pfad achten! RewriteEngine On RewriteBase / RewriteCond %{QUERY_STRING} .*author=(.+.?) [NC] RewriteRule (.*) /wordpress/?author= [NC,L,R=301]
Datei-Bearbeitung über Web-Interface deaktivieren
Da diese Dateien normalerweise nicht oder nur selten geändert werden müssen und diese Änderungen auch ganz einfach über die Shell und/oder einen Text-Editor durchzuführen sind, empfehle ich, diese Funktionen zu deaktivieren.
Fügen Sie der Datei wp-config.php
folgenden Parameter hinzu:
/**
* Disable File-Editing
*/
define('DISALLOW_FILE_EDIT', true);
Auslesen der Wordpress-Version verhindern
Zum einen ist es für einen Angreifer deutlich schwieriger einen Exploit auszunutzen, wenn die Version des Zielsystems nicht bekannt ist. Ein Exploit ist in der Regel an eine bestimmte Versionsnummer gebunden.
/wp-includes/functions.php
wird nach einem Update in der Regel überschrieben.Die Änderung muss also nach jedem Update neu hinzugefügt werden.
Fügen Sie der Datei /wp-includes/functions.php
folgende Parameter hinzu:
/**
* Removing WordPress version number from the header and RSS
*
*/
function remove_wordpress_version() {
return '';
}
add_filter('the_generator', 'remove_wordpress_version');
/**
* Removing WordPress version number from Scripts and CSS
*
*/
function remove_version_from_style_js( $src ) {
if ( strpos( $src, 'ver=' . get_bloginfo( 'version' ) ) )
$src = remove_query_arg( 'ver', $src );
return $src;
}
add_filter( 'style_loader_src', 'remove_version_from_style_js');
add_filter( 'script_loader_src', 'remove_version_from_style_js');