Benutzer-Werkzeuge

Webseiten-Werkzeuge


Seitenleiste

Was fehlt?

Es liegt in der Natur der Sache: Ein Wiki ist niemals fertig. Wir geben uns große Mühe, mit der Entwicklung Schritt zu halten; lassen Supportanfragen direkt in neue Artikel einfließen … aber auch wir sind nicht perfekt. Wenn du hier nicht fündig wirst: Nicht schmollen - Bescheid sagen! Unter hallo@uberspace.de steht dir unser Team gerne bereit. Hand drauf!

webserver:htaccess

.htaccess-Dateien

.htaccess-Dateien sind ein einfacher Weg, um Konfigurationsanweisungen vornehmen zu können, die normalerweise in der Webserver-Konfiguration stehen müssten - auf die du beim shared hosting natürlich keinen Zugriff hast. Es handelt sich hierbei um einfache Textdateien mit Apache-Konfigurationsanweisungen, die du mit einem beliebigen Texteditor erstellen kann.

Mit .htaccess-Dateien kannst du viele spannende Dinge tun; einige Möglichkeiten möchten wir dir hier gerne vorstellen. Eine Einführung in .htaccess-Dateien findest du auch auf apache.org.

Achtung, Falle: .htaccess-Dateien werden immer vom Root-Verzeichnis des Servers aus verarbeitet, nicht erst ab dem DocumentRoot. Das ist dann problematisch, wenn du mehrere Domains hast und dabei DocumentRoots eingesetzt, die unterhalb des primären DocumentRoots, dem html-Verzeichnis liegen. Konkretes Beispiel:

Legst du nun eine /var/www/virtual/erna/html/.htaccess-Datei an, so gilt diese auch für http://blog.erna-von-mattern.nat/, was zu unvorhergesehenen Überraschungen führen könnte. Wir empfehlen dir daher, separate DocumentRoots nur neben html anzulegen, also z.B. im konkreten Fall /var/www/virtual/erna/blog als DocumentRoot zu verwenden.

Bitte beachte außerdem, dass du nicht jede Apache-Konfigurationsanweisung auch in einer .htaccess-Datei verwenden kannst. In der Kurzreferenz der Direktiven in der Apache-Dokumentation sind alle Direktiven, die in .htaccess-Dateien zulässig sind, in der vorletzten Spalte mit „h“ gekennzeichnet. In den Details jeder Direktive gibt es außerdem eine einführende Box, die unter anderem aufführt, in welchem Kontext eine Direktive verwendet werden kann; auch hier wird „.htaccess“ extra aufgeführt, wenn eine Direktive in .htaccess-Dateien zulässig ist.

Verzeichnisschutz

Einer der häufigsten Gründe für den Einsatz von .htaccess-Dateien ist, bestimmte Verzeichnisse mit einem simplen Passwortschutz zu versehen. Der Vorteil ist, dass das ohne zusätzliche Software funktioniert, also auch für Verzeichnisse, in denen lediglich statische Dateien (z.B. Fotos) liegen. Und so geht's:

Du brauchst zunächst eine Passwortdatei, in der die Benutzer und ihre Passwörter gespeichert werden; letztere verschlüsselt. Am einfachsten lässt sich diese Datei mit dem Programm htpasswd verwalten. So legst du sie an und trägst den ersten Benutzer ein:

[larissa@krypton ~]$ htpasswd -m -c /var/www/virtual/larissa/.htuser onkeljonas
New password: 
Re-type new password: 
Adding password for user onkeljonas

Dieser Befehl legt eine Passwortdatei an und trägt den User onkeljonas ein. Hierbei wird interaktiv - zweimal, zum Schutz vor Vertippern - das gewünschte Passwort abgefragt. Es gibt zwar auch einen sogenannten batch mode, bei dem man das Passwort direkt als Parameter mit übergeben kann; hier wäre es allerdings dann in der Prozessliste des Servers für einen kurzen Moment sichtbar und könnte von anderen Usern mitgelesen werden. Das Argument -m bedeutet, dass der Hashwert des Passworts mittels MD5 mit einem Salt generiert wird, was wesentlich schwerer zu knacken ist als die Standardverschlüsselung via crypt(), die htpasswd ansonsten benutzt (für den Fall, dass deine Passwortdatei mal in falsche Hände geraten sollte).

Der Ort und auch der Name der .htuser-Datei ist nicht festgelegt; er muss jedoch unterhalb von /var/www/virtual/larissa liegen, damit der Webserver sie auch lesen kann, und es empfiehlt sich, die Datei außerhalb des DocumentRoots zu lagern, so dass sie nicht übers Netz heruntergeladen werden kann. Die Benennung mit einem führenden „.“ sorgt dafür, dass der Apache die Datei auch dann nicht zum Download anbietet, wenn sie innerhalb des DocumentRoots liegt (wovon wir aber ohnehin ausdrücklich abraten).

Zum Anlegen weiterer User lässt du das -c (das für create steht) einfach weg, ansonsten überschreibst du mit dem neuen User den bisherigen User.

Gibst du einen bereits bestehenden Usernamen an, so ändert htpasswd dessen Passwort:

[larissa@krypton ~]$ htpasswd -m /var/www/virtual/larissa/.htuser onkeljonas
New password: 
Re-type new password: 
Updating password for user onkeljonas

Schließlich fehlt noch das Löschen von Usern, das du mit -D (Achtung, Großschreibung!) erzielst:

[larissa@krypton ~]$ htpasswd -D /var/www/virtual/larissa/.htuser onkeljonas
Deleting password for user onkeljonas

Nun zur eigentlichen .htaccess-Datei. Hierzu kannst du dir einfach diesen Schnipsel kopieren und in deine .htaccess-Datei im gewünschten Verzeichnis einfügen:

AuthType Basic
AuthName "Geheimer Bereich"
AuthUserFile /var/www/virtual/larissa/.htuser
Require valid-user
# oder auch:
#Require user onkeljonas

Den AuthName kannst du natürlich ändern; wichtig ist, dass er in Anführungszeichen steht, zumindest sobald die Bezeichnung aus mehr als einem Wort besteht.

Den Pfad zum AuthUserFile musst du auf den Pfad deiner .htuser-Datei anpassen.

Bei Require kannst du angeben, welche Benutzer Zugriff haben sollen. Hierbei kannst du entweder user und dann einen oder auch mehrere User aus einer .htuser-Datei angeben (mehrere User einfach mit Leerzeichen trennen), oder du verwendest den speziellen Wert valid-user, um einfach sämtliche User, die in deiner .htuser-Datei existieren, zu autorisieren.

Das war's auch schon! Detaillierte weitergehende Informationen, die auch die Bildung von Usergruppen umfassen findest du in der offiziellen Authentifizierungs-Doku auf apache.org.

Verzeichnisinhalte auflisten lassen

Hinterlegst du eine Datei in deinem ~/html-Verzeichnis, so ist diese zwar für jeden erreichbar, der den Dateinamen kennt, doch lässt sich der Verzeichnisinhalt nicht auflisten. Nun kann es aber natürlich sein, dass du genau das möchtest. Insofern gibt es eine ganz triviale Möglichkeit um das von uns von Haus aus ausgeschaltete Auflisten von Verzeichnisinhalten zu aktivieren. Dazu erstellst du einfach eine .htaccess-Datei in einem beliebigen, freizugebenden Verzeichnis unterhalb von ~/html (oder einem Unterverzeichnis in /var/www/virtual/larissa/) mit folgendem Inhalt:

Options +Indexes 

Beachte aber, dass der Apache die .htaccess-Datei hierarchisch auswertet. Falls also ~/html/unwichtig/ freigegeben werden soll, ~/html/unwichtiges/docheherwichtig hingegen nicht, so muss in dem Unterverzeichnis docheherwichtig das Listen des Verzeichnisinhalts wieder deaktiviert werden:

Options -Indexes

Beachte aber, dass das für den Webserver erreichbare ~/html-Verzeichnis kein guter Speicherort für kritische Informationen oder wichtige Daten ist, die für niemanden erreichbar sein sollen.

HTTPS erzwingen

Ein Teil unserer Webserver nutzt noch mod_ssl, während unsere neueren Hosts mit Pound als HTTPS-Frontend arbeiten. mod_ssl definiert bei HTTPS-Verbindungen eine Servervariable namens HTTPS, während HTTPS-Verbindungen über Pound eine Umgebungsvariable namens HTTPS bereitstellen. Es ist aber ohne Probleme möglich, in einer .htaccess-Datei auf beide Möglichkeiten Rücksicht zu nehmen. So kannst du alle Requests, die keine dieser Variablen haben, grundsätzlich blockieren:

RewriteEngine On
RewriteCond %{HTTPS} !=on
RewriteCond %{ENV:HTTPS} !=on
RewriteRule .* - [F,L]

Oder, noch schicker - du kannst einen Redirect auf die HTTPS-URL auslösen:

RewriteEngine On
RewriteCond %{HTTPS} !=on
RewriteCond %{ENV:HTTPS} !=on
RewriteRule .* https://%{SERVER_NAME}%{REQUEST_URI} [R=301,L]

Bitte beachte, dass wir HTTPS mittels Server Name Indication realisieren, was mit älteren Clients, insbesondere mit dem Internet Explorer unter Windows XP und mit älteren Android-Versionen nicht funktioniert. Michael Jaser hat - vielen Dank dafür - Regeln entwickelt, die nur jene Clients umleiten, die SNI beherrschen, was vertretbar ist, wenn TLS nur „nice to have“ ist, aber kein geschäftskritisches Feature, weil keine sensiblen Daten übermittelt werden.

Wenn du eine eigene Domain aufgeschaltet hast, möchtest du vermutlich auch eigene Zertifikate benutzen, damit die Browser keine Warnung werfen. Das ist bei uns kein Problem.

URLs umschreiben

Eine der mächtigsten Möglichkeiten von .htaccess-Dateien ist, aufgerufene URLs auf andere URLs umzuschreiben. Nicht umsonst wird das dahinterstehende Modul mod_rewrite als „damned cool voodoo, but still voodoo“ bezeichnet. Es sei daher an dieser Stelle ausdrücklich auf den offizielle Apache-Dokumentation verwiesen werden, insbesondere auf das Intro zu mod_rewrite als auch auf den Rewrite Guide, der neben einer detaillierten Einführung auch viele praktische Beispiele liefert, die hier den Rahmen sprengen würden.

Exemplarisch zeigen wir dir aber ein Beispiel aus der Realität: Viele Webapplikationen bringen nämlich bereits fertige .htaccess-Dateien mit, die oftmals insbesondere für „schöne“ URLs sorgen, beispielsweise bei DokuWiki:

RewriteEngine On
RewriteRule ^$                        doku.php  [L]
RewriteCond %{REQUEST_FILENAME}       !-f
RewriteCond %{REQUEST_FILENAME}       !-d
RewriteRule (.*)                      doku.php?id=$1  [QSA,L]

Die erste Zeile sorgt dafür, dass die Startseite des Verzeichnisses, wenn also eine leere URL (dafür steht ^$) aufgerufen wurde, automatisch auf die doku.php umgeschrieben wird. Davon bekommt der Anwender nichts mit: Er sieht einfach nur https://uberspace.de/dokuwiki/, obwohl faktisch https://uberspace.de/dokuwiki/doku.php aufgerufen wird.

Die nächsten beiden Zeilen sind Bedingungen: Die RewriteRule in der vierten Zeile greift nur, wenn die beiden RewriteConds passen. Diese prüfen, ob der aufgerufene Dateiname physisch als Datei (-f) oder Verzeichnis (-d) auf der Festplatte vorliegt, und nur falls nicht, so wird die URL so umgeschrieben, dass aus dem aufgerufenen Dateinamen den URL-Parameter id macht und auch hier die doku.php aufruft. Im Moment liest du beispielsweise die URL https://uberspace.de/dokuwiki/webserver:htaccess - faktisch wurde das intern aber auf die neue URL https://uberspace.de/dokuwiki/doku.php?id=webserver:htaccess umgeschrieben. Ein vergleichbares Regelwerk benutzen übrigens auch andere Web-Applikationen wie z.B. Typo3.

Hostnamen "normalisieren"

Wir werden häufiger gefragt, wie dafür gesorgt werden kann, dass eine Webseite in Suchergebnissen von Suchmaschinen nur unter einer Domain auftaucht, statt zusätzlich noch unter $USER.$HOST.uberspace.de. Eine andere häufige Frage, die in die gleiche Richtung geht ist, wie z.B. dafür gesorgt werden kann, dass immer vorne die Subdomain „www.“ angefügt wird. Beides lässt sich wie folgt lösen:

RewriteEngine On
RewriteCond %{HTTP_HOST} !=www.example.com
RewriteRule (.*) http://www.example.com/$1 [R=301,L]

Zu Deutsch: Wenn der verwendete Hostname nicht www.example.com ist, dann leite um auf www.example.com.

Das sorgt zwar nicht dazu, dass die Seite nicht mehr über $USER.$HOST.uberspace.de erreichbar ist, aber es sorgt dafür, dass Zugriffe über $USER.$HOST.uberspace.de immer auf die richtige Domain umgeleitet werden. Die meisten Suchmaschinen interpretieren das dann genau so wie gewünscht und zeigen die Ergebnisse nur noch unter dieser Domain.

RewriteBase

Wenn Du Rewrite-Rules in Unterordnern verwendest, insbesondere dann wenn diese Unterordner als Pseudo-DocumentRoots fungieren (z.B. bei Subdomains), benötigst du ein RewriteBase-Statement:

RewriteBase /

RewriteRule mit Proxy

Viele Dienste wie z.B. Ghost, etherpad-lite und node.js im Allgemeinen lauschen auf einem Port, der erst mal nicht von draußen erreichbar ist. In der Standardkonfiguration ist das meistens 8080 oder irgendwas anderes, was du auf keinen Fall so lassen solltest. Warum? Weil du bestimmt nicht der einzige bist, immerhin betreiben wir hier shared hosting und die Möglichkeit, dass jemand anderes genau das gleiche vor hat wie du, ist gar nicht so gering.

Für die Wahl deines Ports gelten Regeln! Bitte prüfe vorher, ob der Port noch frei oder schon belegt ist.

Wie bekommst du diesen Dienst jetzt nach draußen?

Erst mal ein paar Eckdaten: Gehen wir mal davon aus, dass du einen Dienst auf Port 64223 eingerichtet hast. Dein Uberspace heißt mareike auf Host neon.uberspace.de und du möchtest, dass der Dienst unter meindienst.meinedomain.tld erreichbar ist. Die Domain hast du natürlich vorher auf deinen Uberspace aufgeschaltet.

Der Pfad auf deinem Uberspace lautet also: /var/www/virtual/mareike/meindienst.meinedomain.tld

Auch hier hilft dir eine RewriteRule in deiner .htaccess, die in den eben beschriebenen Pfad gehört:

[mareike@neon html]$ cat .htaccess
RewriteEngine On
RewriteRule (.*) http://localhost:64223/$1 [P]

Das [P] steht für Proxy und wird hier genauer erläutert.

HTTPS erzwingen

Im Support stoßen wir immer mal wieder darauf, dass es Probleme mit dem Erzwingen von HTTPS in Verbindung mit der Proxy-Anweisung in der .htaccess gibt. Das basiert auf einem Missverständnis, die Proxy-Anweisung [P] wirkt nämlich gleichzeitig noch wie ein [L], alle nachfolgenden Anweisungen in der .htaccess werden also ignoriert. Die Reihenfolge ist also ausschlaggebend:

[mareike@neon html]$ cat .htaccess
RewriteEngine On
RewriteCond %{HTTPS} !=on
RewriteCond %{ENV:HTTPS} !=on
RewriteRule .* https://%{SERVER_NAME}%{REQUEST_URI} [R=301,L]
RewriteRule (.*) http://localhost: 64223/$1 [P]

Achtung Fallstrick: Wir empfehlen dir ausdrücklich den Gebrauch von Subdomains, da viele Dienste es leider nicht hinbekommen, relative Pfade auszuspielen. Ein Betrieb in einem Unterordner (meinedomain.tld/meindienst) wird damit leider unmöglich.

Kompression

Hin und wieder kommt die Frage auf, wie der Apache instruiert werden kann, Inhalte automatisch zu komprimieren. Das geht bei uns prinzipiell genau so wie die Dokumentation von Apache 2.2 es beschreibt. Trage dazu in der htaccess-Datei der Seite folgende Anweisung ein:

AddOutputFilterByType DEFLATE text/html text/plain text/xml text/css application/javascript text/javascript

Die Kompression funktioniert für statische Dateien und durch CGI-Scripte generierte Ausgaben. Bei CGI-Scripts gehört die htaccess-Datei mit der Anweisung in das Verzeichnis des Scripts (cgi-bin). Dies gilt jedoch nicht für PHP-Scripts, die bei uns unter FastCGI laufen. Hier muss die Kompression bereits in der Anwendung vorgenommen werden; das geschieht durch die Anweisung zlib.output_compression = On, die Du in Deiner php.ini eintragen kannst.

Bei vielen Anleitungen und Beispielen, die sich im Netz finden lassen, wird die Anweisung per IfModule mod_filter.c bedingt. Das ist dann ein Problem, wenn du auf einem unserer älteren Hosts arbeitest, auf dem Apache 2.2 läuft. In dieser Version gab es den mod_filter noch nicht, sondern die Funktionalität war im Apache fest verbaut. In dem Fall entferne bitte die Bedingung, dann klappt es auch mit der Kompression. Ab Version 2.3.7 klappt es mit dem IfModule und du musst nichts weiter tun.

Was nicht geht

Aus Sicherheitsgründen kannst du Options +FollowSymLinks nicht verwenden. Das ist aber kein Problem: Der Apache stellt mit SymLinksIfOwnerMatch eine Option bereit, die im Wesentlich exakt das gleiche tut wie FollowSymLinks, aber gleichzeitig überprüft, ob das Ziel dem gleichen User gehört wie der Link selbst. Das Schöne daran: Symlink-Attacken sind ausgeschlossen aber der Webserver kann trotzdem Symlinks folgen.

Die Lösung ist also …

Options +SymLinksIfOwnerMatch

… in die .htaccess einzutragen bzw. Options +FollowSymLinks durch den Eintrag oben zu ersetzen.

PHP-Einstellungen

In einigen Dokumentationen wird geraten, PHP-Einstellungen in .htaccess-Dateien unterzubringen (Stichworte: php_value, php_flag, php_admin_value, php_admin_flag). Das funktioniert aber nur, wenn PHP als Webserver-Modul zum Einsatz kommt, was bei uns aus Sicherheitsgründen nicht der Fall ist.

Du hast aber bei uns sowieso die Möglichkeit, eine eigene php.ini zu verwenden (und die Empfehlung, PHP-Einstellungen über eine .htaccess-Datei zu regeln, entspricht üblicherweise dem Umstand, dass genau das bei den meisten anderen Providern eben gerade nicht geht), was wir hierfür auch ausdrücklich empfehlen.

Möchtest du unbedingt bei der .htaccess-Variante bleiben, so gibt es die PECL-Erweiterung htscanner, die zur Laufzeit entsprechende Einträge aus .htaccess-Dateien heraussucht und umsetzt. Das ist allerdings deutlich weniger performant als der Weg über die php.ini. Wir haben htscanner auf unseren Hosting-Servern - mangels Bedarf - in der Regel nicht vorinstalliert. Solltest du es benötigen, wende dich bitte an uns.

SetEnv

Du kannst zwar mittels SetEnv Umgebungsvariablen setzen; diese werden jedoch nicht an deine Scripts durchgereicht. Der Grund dafür ist, dass suEXEC nur eine definierte Liste von Umgebungsvariablen durchlässt und alle anderen sperrt. Im entsprechenden Wiki-Artikel haben wir für dich Details dazu zusammengestellt.

Hintergrund: die VirtualHost Konfiguration

Falls Du Dich fragst, wie denn eigentlich die Konfiguration Deines VirtualHosts aussieht, geben wir hier mal ein generisches Beispiel:

<Directory /var/www/virtual/beispieluser>
AllowOverride AuthConfig FileInfo Indexes Limit Options=ExecCGI,Includes,Indexes,MultiViews,SymLinksIfOwnerMatch
Options +Includes
</Directory>

<VirtualHost 95.143.172.95:81>
ServerName beispieluser.andromeda.uberspace.de
ServerAlias *.beispieluser.andromeda.uberspace.de
ServerAdmin support@uberspace.de
SuexecUserGroup beispieluser beispieluser
DocumentRoot /var/www/virtual/beispieluser/html
ScriptAlias /cgi-bin /var/www/virtual/beispieluser/cgi-bin
ScriptAlias /fcgi-bin /var/www/virtual/beispieluser/fcgi-bin
Include /etc/httpd/conf/dyncontent.conf

RewriteEngine On

# PHP expects a "HTTP_AUTHORIZATION" header to correctly provide PHP_AUTH_USER and PHP_AUTH_PW
RewriteRule .* - [E=HTTP_AUTHORIZATION:%{HTTP:Authorization}]

# If there is a host-specific pseudo-DocumentRoot, use it instead of the default one
RewriteCond %{REQUEST_URI} !^/f?cgi-bin/
RewriteCond /var/www/virtual/beispieluser/%{HTTP_HOST} -d
RewriteRule (.*) /var/www/virtual/beispieluser/%{HTTP_HOST}/$1

</VirtualHost>

Der ungewöhnliche Port 81 ergibt sich dadurch, daß auf den Ports 80 und 443 auf den meisten Hosts (ältere Hosts rüsten wir noch behutsam um) ein Pound-Proxy läuft, der sich dann mit dem Webserver auf Port 81 verbindet. Durch Pound erübrigt sich z.B. die Konfiguration von TLS in den Apache-Configs.

webserver/htaccess.txt · Zuletzt geändert 2015/03/08 13:24 von uber