Bewertung 2


Die Kandidaten sollten in der Lage sein, einen Apache Webserver zu installieren und zu konfigurieren. Dieses Lernziel beinhaltet die Überwachung von Apache-Auslastung und -Performance, die Einschränkung von Benutzerzugriffsrechten, die Konfiguration von mod_perl und PHP-Unterstützung und das Einrichten von Benutzerauthentisierung. Ebenfalls enthalten ist die Konfiguration von Apache Serveroptionen wie z.B. maximale Zahl von Anfragen, minimale und maximale Server- und Clientanzahl.

Schlüsseldateien, Begriffe und Hilfsmittel beinhalten:

  • access.log
  • .htaccess
  • httpd.conf
  • mod_auth
  • htpasswd
  • htgroup

Konfiguration der Logbuchausgabe

Das Ausgabeformat der Logbucheinträge kann durch Einstellungen in der httpd.conf-Datei genau angegeben werden. Dazu sind zwei Schritte notwendig. Zunächst wird über die Direktive LogFormat ein Format bestimmt und mit einem Namen (Nickname) versehen. Es können beliebig viele solcher Formate mit unterschiedlichen Namen formuliert werden. Anschließend wird dann – entweder allgemeingültig für alle Zugriffe oder speziell für jeden virtuellen Server – eine Direktive CustomLog angegeben, zusammen mit dem Dateinamen der Datei, in die das Logbuch geschrieben werden soll und dem Namen des zu verwendenden Formats. Auch diese Direktive kann mehrfach (auch mehrfach pro virtuellem Server) angegeben werden, so dass verschiedene Logbücher mit verschiedenen Formaten verwendet werden können.

Das Format des LogFormat Befehls

Grundsätzlich wird dieser Befehl in der Form

  LogFormat "Zeichenkette mit Formatangaben" Nickname 

angewandt. Innerhalb der Zeichenkette können jetzt beliebige Substitutionen eingesetzt werden, die die folgende Bedeutung haben:

Substitution   Bedeutung
%aIP-Adresse des Clients
%AIP-Adresse des Servers
%BGesendete Bytes ohne HTTP-Header
%bGesendete Bytes ohne HTTP-Header im CLF-Format, also z.B. ein – statt einer 0 wenn keine Bytes gesendet wurden
%cVerbindungsstatus nach Beendigung der Antwort:
‚X‘ = Verbindung wurde unterbrochen
‚+‘ = Verbindung kann nach Ende der Antwort aufrecht erhalten werden
‚-‚ = Verbindung wird nach Antwort beendet.
%{FOOBAR}eInhalt der Umgebungsvariable FOOBAR
%fDateiname
%hHostname des Clients
%HDas angeforderte Protokoll
%{Foobar}iDer Inhalt von Foobar (in der Kopfzeile der an den Server gesendeten Anfrage
%lRemote Logname (über identd falls möglich)
%mDie angeforderte Methode
%{Foobar}nDer Inhalt der Bemerkung Foobar eines anderen Moduls
%{Foobar}oDer Inhalt von Foobar (in der Kopfzeile der Antwort des Servers
%pDer canonical Port des Servers, der die Anfrage bedient
%PDie ProzessID des Child-Prozesses, der die Anfrage bedient
%qDer Query-String (angeführt von einem ? wenn ein Query-String existiert, andernfalls ein Leerstring)
%rDie erste Zeile der Anfrage
%sStatus. Für Anfragen, die intern weitergeleitet wurden ist es der Status der Orginal-Anfrage. %>s gibt immer den Status der letzten Anfrage.
%tZeit im englischen Standard-Format
%{format}tZeit in beliebigem Format. format enthält strftime kompatible Zeitangaben
%TZeit in Sekunden, die benötigt wurden, um die Anfrage zu bearbeiten.
%uRemote User
%UAngeforderte URL ohne eventuelle Query-Strings
%vDer Canonical Servername des Servers, der die Anfrage beantwortet
%VDer Servername entsprechend der Einstellung von UseCanonicalName.

Eine typische Anwendungsform wäre also etwa

  LogFormat "%h %l %u %t \"%r\" %>s %b" meinlog

  CustomLog /var/log/apache/access.log meinlog
  

Wir definieren also zunächst ein Logformat und geben diesem Format den Nickname „meinlog“. Anschließend bestimmen wir mit CustomLog, dass die Datei /var/log/apache/access.log mit diesem definierten Format gefüllt werden soll. In dieser Datei werden sich also jetzt nur Logbucheinträge finden, die genau das Format haben, das wir mit LogFormat bestimmt haben.

Mit Hilfe gut durchdachter Logbuchformate kann eine automatische Überwachung des Servers hinsichtlich Auslastung und Performance sehr einfach mit Scripten realisiert werden.

Einschränkung von Zugriffsrechten

Konfiguration von mod_perl

Normalerweise werden Perl-Scripts von Apache nicht direkt abgearbeitet, sondern über den Shebang-Mechanismus (#!…) wird ein Perl Interpreter gestartet, der seinerseits dann das Script aufruft. Die Standard-Ausgabe des Scripts wird dann an den Webserver weitergeleitet und von ihm an den Client geschickt.

Da diese Technik relativ langsam ist, weil für jedes auszuführende Script zunächst einmal der Perl-Interpreter geladen werden muss, wurde eine eingebettete Form von Perl entwickelt. Das Apache-Modul mod_perl bietet die Möglichkeit, dass der Webserver selbst zum Perl-Interpreter wird, also Perl-Programme direkt abarbeiten kann.

Nachdem das Modul installiert ist, muss die Konfigurationsdatei des Webservers an ein paar Stellen angepasst werden, damit mod_perl tatsächlich geladen und aktiviert wird.

Notwendige Angaben in httpd.conf sind:

  ...
  
  # Perl Modul laden
  LoadModule perl_module /usr/lib/apache/1.3/mod_perl.so
  
  ...
  
  # Handler fuer Perl-Scripts definieren
  AddHandler  perl-script .pl
  PerlHandler Apache::Registry
  PerlSendHeader On
  
  ...
  
  # Wenn das Perl-Modul installiert ist, wird es aktiviert
  <IfModule mod_perl.c>
    Alias /perl/ /var/www/perl/ # Oder wo auch immer die Scripts liegen
    <Location /perl>
      SetHandler perl-script
      PerlHandler Apache::Registry
      Options +ExecCGI
    </Location>
  </IfModule>  

Mit dieser Konfiguration ist es jetzt möglich, Perl-Scripts im Verzeichnis /var/www/perl direkt vom Webserver ausführen zu lassen. Voraussetzungen sind dafür nur, dass der Webserveruser Zugriff auf das Verzeichnis hat und die dort liegenden Scripts für ihn ausführbar sind.

Die Scripts müssen keine Shebang-Zeile aufweisen, sie stört aber nicht, wenn sie existiert.

Konfiguration von mod_php

Die Sprache PHP bietet im Gegensatz zu Perl die Möglichkeit, direkt in HTML-Dateien Programmcode einzubetten, der dann vom Webserver ausgeführt wird. Die Dateien tragen dann die Endung .php oder .php3 (ältere Version) und werden vor der Versendung durch den Server zuerst von ihm abgearbeitet.

Damit der Webserver PHP-fähig wird, muss das Modul mod_php (oder ähnlich) installiert werden. Auch für diesen Fall sind einige Änderungen in httpd.conf nötig, um den Webserver zu veranlassen, das Modul auch zu laden.

  ...
  
  # Modul laden  
  LoadModule php4_module /usr/lib/apache/1.3/libphp4.so
  
  ...
  
  # Dateiendung festlegen und mit Typ verbinden
  AddType application/x-httpd-php .php
  AddType application/x-httpd-php-source .phps
  

Nach einem Neustart (apachectl stop;apachectl start) steht die PHP-Fähigkeit jetzt zur Verfügung.

Zugriffskontrolle für bestimmte Rechner

Manche Verzeichnisse (oder URLs oder Dateien) sollen nur von bestimmten Rechnern oder Domains aus zu sehen sein. Um das zu erreichen, gibt es eine Handvoll Befehle, die auch immer innerhalb der verschiedenen Klammerungen stehen, die die entsprechenden Verzeichnisse oder Dateien beschreiben. Dazu können in der Datei httpd.conf bestimmte Verzeichnisse oder Dateien mit speziellen Optionen ausgestattet werden.

Grundsätzlich gibt es drei verschiedene Anweisungen, die alle ein HTML-ähnliches Format benutzen. Das heisst, sie arbeiten mit Tags in spitzen Klammern und entsprechenden Abschlusstags mit vorangestelltem Slash:

VerzeichnisseDateienURLs
<Directory „Verzeichnisname„> Anweisungen </Directory><Files „Dateinamenmuster„> Anweisungen </Files><Location „URL„> Anweisungen </Location>

Der Unterschied zwischen Location und Directory ist einfach der, dass sich das Directory auf absolute Pfade bezieht, die Location aber nur auf die URL aus der Sicht des Webservers. Der Verwalter muss also bei der Location nicht unbedingt wissen, in welchem Verzeichnis sich die DocumentRoot befindet.

Um jetzt einzelnen Rechnern oder Domainmitgliedern Zugriff zu erlauben (oder zu verbieten) können in die entsprechenden Klammern bestimmte Anweisungen gesetzt werden, die diese Rechte steuern.

Zunächst wird festgelegt, in welcher Reihenfolge die Regeln abgearbeitet werden. Dazu dient die Direktive Order, die nur zwei verschiedene Aufrufformen anbietet:

  Order allow,deny

oder

  Order deny,allow

Die einzelnen Regeln werden festgelegt mit den Befehlen

  Deny from Rechnername oder IP-Adresse oder Muster
  Allow from Rechnername oder IP-Adresse oder Muster

Mögliche Angaben über Rechnernamen, IP-Adressen oder Muster können folgende Formate aufweisen: Der Begriff all Alle Clients, egal welche Namen oder Adressen Ein Domainname wie mydomain.de Alle Rechner, die Mitglieder dieser Domain sind Eine vollständige IP-Adresse wie 123.45.67.89 Genau der Rechner mit dieser Adresse Eine unvollständige IP-Adresse wie 10.230 Alle Rechner deren IP-Adressen mit 10.230 beginnen Eine Adresse mit Maske wie 10.230.0.0/255.255.0.0 oder 10.230.0.0/16 Alle Rechner des angegebenen Subnetzes.

Zwei Beispiele sollen die Anwendung dieser Technik erläutern:

  <Directory /usr/local/httpd/htdocs/test>
    Order allow,deny
    Allow from all
  </Directory>

Das Verzeichnis /usr/local/httpd/htdocs/test darf von aller Welt angesehen werden. Stattdessen könnten wir aber auch schreiben

  <Directory /usr/local/httpd/htdocs/test>
    Order deny,allow
    Deny from all
    Allow from 10.230
  </Directory>

Das Verzeichnis darf jetzt nur von Rechnern angesehen werden, die aus dem Netz 10.230.x.y stammen.

Userauthentifizierung mit mod_auth

Jedes der geklammerten Elemente kann auch über eine Art Userauthentifizierung geschützt werden. Dazu müssen zunächst einmal User- bzw. Gruppendateien angelegt werden. In der Klammerung kann also stehen:

  AuthUserFile /etc/httpd/passwd
  AuthGroupFile /etc/httpd/group

Die Namen und Pfade der Dateien sind frei wählbar. Beginnen sie nicht mit einem Slash (sind also keine absolute Pfade), so werden sie vom ServerRoot aus gesucht. Die Passwortdatei enthält pro User eine Zeile im Format

  Username : verschl.Passwort

die Gruppendatei hingegen hat das Format:

  Gruppenname : User1 User2 User3

Mit dem Unixbefehl htpasswd können beliebige Passwortdateien angelegt und verwaltet werden, die Gruppendateien können mit jedem beliebigen Editor angelegt werden. Die Syntax für htpasswd ist – falls die Passwortdatei noch nicht existiert:

  htpasswd -c Passwortdatei Username

Falls die Datei schon existiert sollte das -c weggelassen werden.

Zu den Angaben der Dateien brauchen wir noch zwei weitere, einmal den Typ der Authentifizierung und zum Anderen eine Textzeile, die im Passwortdialog dargestellt wird. Beide sind notwendig, damit es funktioniert.

  AuthType Basic
  AuthName "Zugriff für große Geheimnisse"

Mit dem Befehl Require können jetzt Bedingungen formuliert werden, wer auf das Verzeichnis zugreifen darf. Dabei erwartet Require eine der folgenden Formen:

Require user Username

Nur der genannte User – oder die genannten User (mit Leerzeichen voneinander getrennt) dürfen auf das Verzeichnis (oder die URL oder die Datei) zugreifen.

Require group Gruppenname

Nur Mitglieder der genannten Gruppe – oder der Gruppen dürfen zugreifen.

Require valid-user

Jeder dem System bekannte User (der also einen Eintrag in der angegebenen Passwortdatei hat) darf zugreifen.

Das folgende Beispiel zeigt ein solchermaßen geschütztes Verzeichnis:

  <Directory /usr/local/httpd/htdocs/test>
    AuthType Basic
    AuthName "Zugriff für große Geheimnisse"
    AuthUserFile /etc/httpd/passwd
    Require user efka
  </Directory>

Durch die Angabe beliebiger Passwortdateien können verschiedene Verzeichnisse so für verschiedene User zugänglich gemacht werden, ohne daß die verschiedenen Usereinträge sich stören würden. Es ist theoretisch sogar denkbar, die Passwortdatei in das zu schützende Verzeichnis zu legen, allerdings ist das kein guter Stil.

.htaccess Dateien

Die gesamten Einstellungen, die oben beschrieben wurden, sind in der zentralen Konfigurationsdatei natürlich nur dem User zugänglich, der Zugriff auf diese Datei hat und den Webserver nach einer Änderung neu starten kann.

Um auch anderen Usern die Möglichkeit zu geben, derartige Einstellungen vorzunehmen, gibt es eine sehr elegante Möglichkeit mit den sogenannten .htaccess-Dateien.

Dabei handelt es sich um Dateien, die direkt in ein zu schützendes Verzeichnis abgelegt werden und die genau die selben Einstellungen ermöglichen, wie oben besprochen. Diese Dateien werden jedesmal vom Webserver automatisch eingelesen, sobald eine Anfrage in ein Verzeichnis wechseln will. Der Webserver muß also nicht neu gestartet werden und jeder User kann in sein Verzeichnis solche Dateien ablegen.

Der Name dieser Dateien ist normalerweise .htaccess, das muß aber nicht zwangsläufig so sein, es ist einstellbar in der zentralen Konfigurationsdatei. Mit der Direktive

  AccessFileName .htaccess

wird hier der Name der Zugriffsdatei festgelegt. Zusätzlich muß aber – auch in der zentralen Datei – jedem Verzeichnis noch erlaubt werden, solche Zugriffsdateien zu verwenden. Dazu gibt es die Direktive AllowOverride. Sie legt fest, ob die zentral verwalteten Einstellungen durch Zugriffsdateien in einem Verzeichnis verändert werden dürfen. Diese Anweisung hat innerhalb von <Directory> Blöcken gültigkeit. Die wichtigsten Formen sind:

AllowOverride None

Zugriffsdateien im Verzeichnis werden nicht ausgewertet.

AllowOverride All

Zugriffsdateien im Verzeichnis werden ausgewertet und alle Features sind erlaubt.

Außerdem existieren noch die – seltener gebrauchten Einschränkungen:

AllowOverride AuthConfig

Zugriffsdateien im Verzeichnis werden ausgewertet. Nur Direktiven für die User/Gruppenauthentifizierung sind erlaubt.

AllowOverride Limit

Zugriffsdateien im Verzeichnis werden ausgewertet. Nur Direktiven für die Domain/Rechner-Zugriffssteuerung sind erlaubt.

AllowOverride Options

Zugriffsdateien im Verzeichnis werden ausgewertet. Nur Direktiven für Optionen sind erlaubt.

Die letztgenannten Angaben sind auch kombinierbar, etwa in der Form

  AllowOverride AuthConfig Limit

Wenn diese Voraussetzungen erfüllt sind, dann kann ein User eine solche Zugriffsdatei in ein Verzeichnis legen und damit individuell bestimmen, welche Eigenschaften dieses Verzeichnis hat. Eine exemplarische Zugriffsdatei könnte also z.B. folgendermaßen aussehen:

  # .htaccess für das Verzeichnis foo
  
  # Zuerstmal die Zugriffsdaten
  AuthType Basic
  AuthName "Zugriff auf FOO"
  AuthUserFile /etc/httpd/passwd
  Require valid-user

  # In diesem Verzeichnis sind CGI-Scripts erlaubt
  Options +ExecCGI 
  
  # Nur Rechner aus dem Netz 10.230.0.0 dürfen zugreifen
  Order deny,allow
  Deny from all
  Allow from 10.230

Wichtige Serveroptionen

ServerType standalone|inetd

Diese Anweisung legt fest, ob der Webserver standalone oder durch inetd gestartet werden soll. Wie schon gesagt ist es nicht empfehlenswert, den Apache durch inetd zu starten, also solte hier der Begriff standalone stehen.

ServerRoot „/usr/local/httpd“

Die Angabe des Verzeichnisses, in dem der Apache seine Dateien vorfindet. Hier liegen in der Regel alle wichtigen Dateien und Verzeichnisse, die der Server zum Betrieb benötigt. Nicht verwechseln mit DocumentRoot.

Port 80

Legt die Portnummer fest, auf der der Webserver läuft. Standardport für HTTP ist Port 80. Wenn hier ein Port unter 1024 angegeben wird, muss der Webserver unter der UID von root gestartet werden. Das ist keine Sicherheitslücke, denn der Webserver startet dann weitere Serverprozesse unter einer anderen UserID.

User Username

Die UserID, unter der die Kind-Prozesse des Servers laufen sollen.

LockFile /var/lock/subsys/httpd/httpd.accept.lock

Das Lock-File des Servers. Diese Datei wird vom Server beim Start angelegt und beim Herunterfahren gelöscht. Damit kann der Server selbst feststellen, ob schon ein Apache-Server im Speicher gestartet ist.

PidFile /var/run/httpd.pid

Auch diese Datei wird vom Server beim Start angelegt. Er schreibt seine ProzessID hier hinein, so daß ein späterer Zugriff – etwa zum Versenden eines Kill-Signals – auf den Server möglich ist, ohne erst lang mit dem ps-Kommando die PID herausfinden zu müssen.

Timeout 300

Die Anzahl von Sekunden, die der Server beim Senden und Empfangen von Daten wartet, bis er aufgibt und einen Timeout-Fehler ausgibt.

Alias Aliasname Realname

Erlaubt es, Verzeichnisse außerhalb des DocumentRoot dem Server zu machen. Der Aliasname ist eine Pfadangabe relativ zum DocumentRoot, der Realname ist ein absoluter Pfad aus der Sicht des Systems. Ist das letzte Zeichen des Aliasnamen ein Slash, so muss der Slash in der URL auch angegeben werden, denn es existiert ja kein Alias ohne diesen Slash.

KeepAlive On

KeepAlive ermöglicht es, mehrere Transfers pro Verbindung zuzulassen (On) oder zu verbieten (Off). Damit wird verhindert, daß wegen jeder einzelnen Nachfrage erneut der komplette TCP-Handshake erfolgen muß.

MaxKeepAliveRequests 100

Dieser Wert bestimmt die maximale Menge der zulässigen aufeinanderfolgenden Verbindungen, ohne erneuten TCP-Handshake. Steht der Wert auf 0, so bedeutet das, daß es keine Einschränkungen gibt (unendlich).

KeepAliveTimeout 15

Die Anzahl von Sekunden nach der Übertragung einer Datei bis zum Beginn der nächsten Nachfrage, die ohne zusätzlichen Handshake stattfinden darf.

StartServers 1

Die Anzahl der Serverprozesse, die beim Start geladen werden sollen.

MinSpareServers 1

Die minimale Anzahl der unbenutzten Serverprozesse (Childs). Wird dieser Wert unterschritten, so werden neue Server gestartet.

MaxSpareServers 1

Die maximale Anzahl unbenutzter Serverprozesse (Childs). Wird dieser Wert überschritten, so werden unbenutzte Serverprozesse heruntergefahren.

MaxClients 150

Die maximale Anzahl gleichzeitig bedienbarer TCP-Verbindungen. Kommen gleichzeitig mehr als angegeben herein, so bekommen die übrigen eine Fehlermeldung und werden nicht mehr bedient.

MaxRequestsPerChild 0

Nach der angegebenen Zahl von abgearbeiteten Aufträgen wird ein Child-Prozess heruntergefahren und durch einen neuen ersetzt. Steht der Wert auf 0, so findet keine Ersetzung statt (0 = unendlich). Damit kann z.B. im Dauerbetrieb festgelegt werden, daß kein Server-Child mehr als 30 Anfragen beantwortet. So wird verhindert, daß ein eventuell hängender Prozess über Tage hinweg den Server stört.