Zum Inhalt springen
DEV-TOOL

.htaccess prüfen: Fehler und 500er finden

Eine geerbte .htaccess Zeile für Zeile verstehen, bevor du sie anfasst. Mit URL-Test und Ketten-Prüfung.

Tool

Die meisten `.htaccess`-Dateien schreibt niemand von null. Man erbt sie: von der alten Agentur, aus einem Blogartikel von 2014, aus dem Support-Ticket eines Hosters. Dieser Prüfer nimmt so eine Datei entgegen und sagt dir für jede Zeile, was sie tut, was daran heute nicht mehr stimmt und was mit einer bestimmten Adresse passiert. Alles im Browser, die Datei verlässt dein Gerät nicht.

01: Anleitung

Wie benutzt du dieses Tool?

  1. Inhalt der `.htaccess` einfügen oder die Datei auswählen. Die Prüfung läuft beim Tippen mit, es gibt keinen Startknopf.
  2. Im Reiter „Zeile für Zeile“ steht unter jeder Direktive, was sie bewirkt. Farbige Rahmen markieren die Zeilen mit Befunden.
  3. Im Reiter „URL testen“ trägst du einen Pfad ein und siehst, welche Regeln der Reihe nach greifen und wo die Anfrage landet.
  4. Die zwei Schalter für Datei und Verzeichnis beantworten die `-f`- und `-d`-Bedingungen. Ohne sie lässt sich nicht entscheiden, ob eine Regel zutrifft.
  5. Im Reiter „Weiterleitungskette“ siehst du, wie viele Sprünge eine Adresse braucht und ob sie bei sich selbst landet.

Was macht der .htaccess-Prüfer?

Er liest eine vorhandene Datei und beantwortet drei Fragen, die ein Generator nicht beantworten kann: was tut diese Zeile, was ist daran falsch, und was passiert mit dieser Adresse.

Der Unterschied zu den verbreiteten Testern ist die Richtung. Die meisten nehmen eine URL und ein paar Regeln entgegen und zeigen, was am Ende herauskommt. Das hilft, wenn man die Regeln selbst geschrieben hat. Wer eine gewachsene Datei geerbt hat, hat aber ein anderes Problem: er weiß nicht, was da steht, und traut sich deshalb nicht, etwas zu löschen. Deswegen steht hier unter jeder Direktive ein Satz in normaler Sprache.

Dazu kommt eine Bewertung, wie schwer sich eine Zeile zurücknehmen lässt. Das Ausschalten des Verzeichnis-Listings ist jederzeit umkehrbar. Ein HSTS-Header mit preload wirkt in jedem Browser weiter, der ihn einmal gesehen hat, unabhängig davon, was der Server danach ausliefert, und aus der Preload-Liste wieder herauszukommen dauert Monate. Beides sieht in einer Textdatei gleich aus. In der Ausgabe nicht.

Warum antwortet der Server nach dem Hochladen mit 500?

Das ist der mit Abstand häufigste Weg, eine Seite mit einer .htaccess abzuschalten, und die Ursache ist fast immer dieselbe: eine Direktive, deren Modul nicht geladen ist.

Man erwartet, dass Apache eine unbekannte Zeile überliest. Das tut er nicht. Er bricht die Anfrage ab, und zwar für die ganze Seite, nicht nur für die betroffene Regel. Im Fehlerlog steht dann Invalid command 'Order', perhaps misspelled or defined by a module not included in the server configuration.

Zwei Gruppen fallen dabei auf. Die erste ist die alte Zugriffssteuerung aus Apache 2.2: Order, Allow from, Deny from, Satisfy. Die Umstiegsdokumentation von Apache nennt seit 2012 Require als Ersatz, aber die alten Zeilen halten sich in Anleitungen, Foren-Antworten und den Standard-Snippets mancher Plugins. Die zweite Gruppe sind Zeilen, die ein Modul brauchen, das auf günstigen Tarifen oft fehlt: Header braucht mod_headers, ExpiresDefault braucht mod_expires, RewriteRule braucht mod_rewrite.

Der Ausweg ist in beiden Fällen derselbe. Ein <IfModule mod_headers.c> um den Block macht aus dem Abbruch ein stilles Überspringen. Die Regel wirkt dann zwar nicht, aber die Seite bleibt online, und man sieht am fehlenden Header, woran es liegt.

Woran erkenne ich eine Endlosschleife?

An zwei Regeln, die sich gegenseitig füttern. Der bekannteste Fall braucht dafür nicht einmal zwei Zeilen in der eigenen Datei.

Eine Regel wie RewriteRule ^(.+)/$ /$1 [R=301,L] entfernt den abschließenden Schrägstrich. Für /blog/ schickt sie den Besucher auf /blog. Ist blog ein echtes Verzeichnis, greift danach mod_dir, das standardmäßig DirectorySlash On gesetzt hat, und hängt den Schrägstrich wieder an. Der Browser folgt, die Regel greift erneut, und nach etwa zwanzig Sprüngen bricht er mit ERR_TOO_MANY_REDIRECTS ab. Der ganze Bereich ist damit nicht erreichbar.

Die fehlende Zeile ist RewriteCond %{REQUEST_FILENAME} !-d direkt über der Regel. Sie nimmt echte Verzeichnisse aus, also genau die Fälle, die mod_dir für sich beansprucht.

Der Prüfer meldet diese Regel als Fehler, und im Reiter für die Weiterleitungskette kannst du es nachstellen: Pfad eintragen, den Schalter für „existiert als Verzeichnis“ setzen, und die Kette zeigt den Sprung.

Welche Regel greift für eine bestimmte Adresse?

Dafür gibt es den URL-Test. Du trägst einen Pfad ein, und das Tool geht die Regeln der Reihe nach durch, wie Apache es täte, und zeigt jede, die zutrifft, mit ihrer Zeilennummer.

Zwei Dinge daran sind wichtiger, als sie aussehen. Erstens der führende Schrägstrich: in einer .htaccess vergleicht Apache das Muster mit dem Pfad, aus dem der erste Schrägstrich bereits entfernt wurde. Eine aus einer Server-Konfiguration kopierte Regel mit ^/blog$ trifft deshalb nie zu, und man sucht den Fehler lange woanders. Der Test bildet das nach.

Zweitens die zwei Schalter für Datei und Verzeichnis. Bedingungen wie %{REQUEST_FILENAME} !-f fragen das Dateisystem des Servers ab, und das kennt ein Browser nicht. Statt zu raten, fragt das Tool dich. Damit werden genau die Regeln entscheidbar, an denen die meisten Anleitungen hängen.

Wo eine Bedingung wirklich nicht auswertbar ist, etwa weil sie an einem Cookie hängt oder mit [OR] verzweigt, wird die Regel nicht angewendet und die Zeile als „nicht ausgewertet“ ausgewiesen. Das Ergebnis ist damit eine untere Schranke: auf dem Server kann zusätzlich etwas greifen, aber was angezeigt wird, greift auch dort.

Was kostet eine Weiterleitungskette?

Ladezeit, und bei Suchmaschinen etwas Ranking. Jeder Sprung ist eine eigene Anfrage mit eigener Latenz, auf einer langsamen Mobilverbindung sind drei Sprünge deutlich spürbar.

Ketten entstehen selten mit Absicht. Sie wachsen, wenn HTTPS-Zwang, www-Kanonisierung und ein alter Einzelredirect nacheinander in derselben Datei stehen. Jede Regel für sich ist richtig, zusammen ergeben sie http://www.beispiel.de/alt auf https://www.beispiel.de/alt auf https://beispiel.de/alt auf https://beispiel.de/neu. Drei Sprünge, wo einer reichen würde.

Der dritte Reiter läuft die Kette ab, die deine eigene Datei erzeugt, und zählt die Sprünge. Landet eine Adresse dabei wieder bei sich selbst, steht das als Schleife da und nicht als funktionierende Weiterleitung.

Welche Zeilen kann das Tool nicht auswerten?

Alles außerhalb des Teils, der in echten Dateien vorkommt. Ausgewertet werden Rewrites samt Bedingungen und Flags, Weiterleitungen über Redirect und RedirectMatch, Header, die Zugriffsdirektiven beider Apache-Generationen, Caching, Kompression, Fehlerseiten, Verzeichnis-Optionen und der Passwortschutz.

Kommt etwas anderes vor, steht daneben ein Hinweis, dass diese Zeile nicht ausgewertet wurde. Sie bleibt unverändert im Ausdruck stehen. Das ist Absicht: eine Prüfung, die unbekannte Zeilen stillschweigend überspringt, gibt am Ende eine Entwarnung, die sie nicht decken kann.

Eine Einschränkung betrifft die Reihenfolge. Apache führt mod_alias und mod_rewrite in getrennten Phasen aus, Redirect und RewriteRule laufen also nicht einfach von oben nach unten. Hier werden sie in Dateireihenfolge ausgewertet, weil das der Reihenfolge entspricht, in der ein Mensch die Datei liest. Mischt eine Datei beides, kann die echte Reihenfolge abweichen, und das steht auch unter dem Ergebnis.

Wie hängt der Prüfer mit dem Generator zusammen?

Sie sind die zwei Richtungen derselben Sache. Der .htaccess-Generator baut eine Datei aus einer Regelauswahl und achtet dabei auf die Modul-Guards, die Apache-Version und die Reihenfolge. Der Prüfer nimmt eine fertige Datei und erklärt sie.

In der Praxis geht man den Weg meist einmal hin und zurück: die geerbte Datei hier durchschauen, die Regeln notieren, die wirklich gebraucht werden, und sie im Generator sauber neu aufsetzen. Was dabei wegfällt, sind die Zeilen, die seit Jahren mitkopiert werden und nichts mehr tun.

Wer den Server wechselt, findet die Übersetzung ins nginx-Format im nginx-Config-Generator. Für die Passwortdatei, auf die AuthUserFile zeigt, gibt es den .htpasswd-Generator.

Hintergrund zur Datei selbst steht in der Apache-Dokumentation zu .htaccess und im Wikipedia-Artikel.

Zuletzt aktualisiert:

Das könnte dir auch gefallen