15.9. Aktive Inhalte

Apache bietet mehrere Möglichkeiten, aktive Inhalte an Clients auszuliefern. Unter aktiven Inhalten versteht man HTML-Seiten, die aufgrund einer Verarbeitung aus variablen Eingabedaten des Clients erstellt wurden. Ein bekanntes Beispiel dafür sind Suchmaschinen, die auf die Eingabe eines oder mehrerer, eventuell durch logische Operatoren wie UND bzw. ODER verknüpfter Suchbegriffe eine Liste von Seiten zurückgeben, in denen diese Begriffe vorkommen.

Mit Apache gibt es drei Wege, um aktive Inhalte zu erstellen:

Server Side Includes (SSI)

Dabei handelt es sich um Anweisungen, die mit Hilfe spezieller Kommentare in eine HTML-Seite eingebettet werden. Apache wertet den Inhalt der Kommentare aus und gibt das Ergebnis als Teil der HTML-Seite mit aus.

Common Gateway Interface (CGI)

Hierbei werden Programme ausgeführt, die innerhalb bestimmter Verzeichnisse liegen. Apache übergibt vom Client übertragene Parameter an diese Programme und gibt die Ausgabe des Programms an den Client zurück. Diese Art der Programmierung ist relativ einfach, zumal man existierende Kommandozeilenprogramme so umbauen kann, dass sie Eingaben von Apache annehmen und Ausgaben an ihn ausgeben.

Module

Apache bietet Schnittstellen, um beliebige Module als Teil der Verarbeitung einer Anfrage ausführen zu können, und gewährt diesen Programmen zudem Zugriff auf wichtige Informationen, wie den Request oder die HTTP-Header. Dies macht es möglich, Programme in die Verarbeitung der Anfrage einzufügen, die nicht nur aktive Inhalte erzeugen können, sondern auch andere Funktionen (wie Authentifizierung) übernehmen können. Die Programmierung solcher Module erfordert etwas Geschick, als Vorteil wiegt eine hohe Performance sowie Möglichkeiten, die sowohl über SSI als auch über CGI weit hinausgehen.

Während CGI-Skripte einfach von Apache aufgerufen werden (unter der Benutzer-ID ihres Eigentümers), wird bei Verwendung von Modulen ein Interpreter in Apache eingebettet, der dann unter der ID des Webservers permanent läuft. Der Interpreter ist „persistent“. Auf diese Weise muss nicht für jede Anfrage ein eigener Prozess gestartet und beendet werden (was einen erheblichen Overhead für Prozessmanagement, Speicherverwaltung usw. nach sich zieht), stattdessen wird das Skript einfach an den bereits laufenden Interpreter übergeben.

Einen Nachteil hat die Sache allerdings: Während über CGI ausgeführte Skripte einigermaßen tolerant gegen nachlässige Programmierung sind, wirkt sich diese bei Verwendung von Modulen schnell nachteilig aus. Der Grund dafür ist, dass bei normalen CGI-Skripten Fehler wie das Nicht-freigeben von Resourcen und Speicher nicht so sehr ins Gewicht fallen, da die Programme nach Bearbeitung der Anfrage wieder beendet werden und damit vom Programm aufgrund eines Programmierfehlers nicht freigegebener Speicher wieder verfügbar wird. Bei Verwendung von Modulen häufen sich die Auswirkungen von Programmierfehlern an, da der Interpreter permanent läuft. Wenn der Server nicht neu gestartet wird, kann der Interpreter ohne weiteres monatelang laufen, da machen sich nicht freigegebene Datenbankverbindungen oder ähnliches durchaus bemerkbar.

15.9.1. Server Side Includes: SSI

Server Side Includes sind in spezielle Kommentare eingebettete Anweisungen, die Apache ausführt. Das Ergebnis wird dann an Ort und Stelle in die Ausgabe eingebettet. Ein Beispiel: Das aktuelle Datum kann man mit <!--#echo var="DATE_LOCAL" --> ausgegeben werden. Hierbei ist das # dem Kommentaranfang <!-- der Hinweis für Apache, dass es sich um eine SSI-Anweisung und nicht um einen gewöhnlichen Kommentar handelt.

SSIs können auf mehrere Arten aktiviert werden. Die einfache Variante ist, alle Dateien, deren Rechte auf ausführbar gesetzt sind, auf Server Side Includes zu untersuchen. Die andere Variante ist, für bestimmte Dateitypen festzulegen, dass sie auf SSIs untersucht werden sollen. Beide Einstellungen werden im Abschnitt 15.7.2.16. “Server Side Includes” erläutert.

15.9.2. Common Gateway Interface: CGI

CGI ist eine Abkürzung für „Common Gateway Interface“. Mit CGI liefert der Server nicht einfach eine statische HTML-Seite aus, sondern führt ein Programm aus, das die Seite liefert. Auf diese Weise können Seiten erstellt werden, die das Ergebnis einer Berechnung sind, beispielsweise das Ergebnis einer Suche in einer Datenbank. An das ausgeführte Programm können Argumente übergeben werden, so kann es für jede Anfrage eine individuelle Antwort-Seite zurückliefern.

Der große Vorteil an CGI ist, dass es eine recht einfache Technik ist. Das Programm muss lediglich in einem bestimmten Verzeichnis liegen und wird dann vom Webserver genauso wie ein Programm auf der Kommandozeile ausgeführt. Die Ausgaben des Programms auf dem Standardausgabekanal (stdout) gibt der Server einfach an den Client aus.

15.9.3. GET und POST

Eingabeparameter können entweder mit GET oder mit POST an den Server übergeben werden. Je nachdem, welche Methode verwendet wird, gibt der Server die Parameter auf unterschiedliche Weise an das Skript weiter. Bei POST übergibt der Server die Parameter auf dem Standardeingabekanal (stdin) an das Programm. Genauso würde das Programm seinen Input erhalten, wenn es in einer Konsole gestartet wird.

Bei GET werden die Parameter vom Server in der Umgebungsvariablen QUERY_STRING an das Programm übergeben. Eine Umgebungsvariable ist eine Variable, die vom System überall verfügbar gemacht wird, ein klassisches Beispiel ist die Variable PATH, die eine Liste von Pfaden enthält, die das System nach ausführbaren Kommandos durchsucht, wenn der Anwender einen Befehl eingibt.

15.9.4. Sprachen für CGI

CGI-Programme können prinzipiell in jeder Programmiersprache geschrieben sein. Typischerweise werden Skriptprachen (interpretierte Sprachen) wie Perl oder PHP verwendet, für geschwindigkeitskritische CGIs kann im Einzelfall auch C oder C++ die erste Wahl sein.

Im einfachsten Fall erwartet Apache diese Programme in einem bestimmten Verzeichnis (cgi-bin). Dieses Verzeichnis lässt sich in der Konfigurationsdatei einstellen, siehe den Abschnitt 15.7. “Konfiguration”.

Ausserdem lassen sich weitere Verzeichnisse freigeben, die Apache dann nach ausführbaren Programmen durchsucht. Dies stellt aber ein gewisses Sicherheitsrisiko dar, da dann jeder Anwender (evtl. böswillige) Programme von Apache ausführen lassen kann. Wenn man ausführbare Programme lediglich in cgi-bin zulässt, kann der Administrator leichter kontrollieren, wer welche Skripte und Programme dort ablegt und ob diese evtl. bösartiger Natur sind.

15.9.5. Aktive Inhalte mit Modulen erzeugen

Es gibt eine Reihe von Modulen für die Verwendung in Apache. Alle im Folgenden beschriebenen Module stehen als Pakete in zur Verfügung. Der Begriff Modul wird in zwei Bedeutungen verwendet. Zum einen gibt es Module, die in Apache eingebaut werden können und dort eine bestimmte Funktion übernehmen, wie zum Beispiel die im Folgenden vorgestellten Module zur Einbettung von Programmiersprachen in Apache.

Zum anderen spricht man in Programmiersprachen von Modulen, wenn man eine abgeschlossene Menge von Funktionen, Klassen und Variablen meint. Diese Module werden in ein Programm eingebunden, um eine bestimmte Funktionalität zur Verfügung zu stellen. Ein Beispiel sind die in allen Skriptsprachen vorhandenen CGI-Module, die das Programmieren von CGI-Anwendungen erleichtern, indem sie unter anderem Methoden zum Lesen der Request-Parameter und zur Ausgabe von HTML-Code zur Verfügung stellen.

15.9.6. mod_perl

Perl ist eine weitverbreitete und bewährte Skriptsprache. Für Perl gibt es eine riesige Menge an Modulen und Bibliotheken (unter anderem auch eine Bibliothek zur Erweiterung der Konfigurationsdatei von Apache). Die Homepage für Perl ist http://www.perl.com/. Eine grosse Auswahl an Libraries für Perl findet man im Comprehensive Perl Archive Network (CPAN): http://www.cpan.org/. Eine deutschsprachige Seite für Perl-Programmierer ist http://www.perlunity.de/.

15.9.6.1. mod_perl einrichten

Um mod_perl unter einzurichten, muss man lediglich das entsprechende Paket installieren (siehe dazu den Abschnitt 15.6. “Installation”). Die erforderlichen Einträge in der Konfigurationsdatei für Apache sind dann ebenfalls schon vorhanden, siehe /etc/apache2/mod_perl-startup.pl. Informationen über mod_perl finden sich vor allem hier: http://perl.apache.org/

15.9.6.2. mod_perl vs. CGI

Im einfachsten Fall kann man ein bisheriges CGI-Skript als mod_perl-Skript laufen lassen, indem man es unter einer anderen URL aufruft. Die Konfigurationsdatei enthält Aliase, die auf das gleiche Verzeichnis verweisen und darin enthaltene Skripte entweder über CGI oder über mod_perl aufrufen. Alle diese Einträge sind in der Konfigurationsdatei bereits eingetragen. Der Alias-Eintrag für CGI lautet:

ScriptAlias /cgi-bin/ "/srv/www/cgi-bin/"

Die Einträge für mod_perl lauten wie folgt:

<IfModule mod_perl.c>
# Provide two aliases to the same cgi-bin directory,
# to see the effects of the 2 different mod_perl modes.
# for Apache::Registry Mode
ScriptAlias /perl/          "/srv/www/cgi-bin/"
# for Apache::Perlrun Mode
ScriptAlias /cgi-perl/      "/srv/www/cgi-bin/"
</IfModule>

Die folgenden Einträge sind für mod_perl ebenfalls nötig. Auch sie sind bereits in der Konfigurationsdatei eingetragen.

#
# If mod_perl is activated, load configuration information
#
<IfModule mod_perl.c>
Perlrequire /usr/include/apache/modules/perl/startup.perl
PerlModule Apache::Registry

#
# set Apache::Registry Mode for /perl Alias
#
<Location /perl>
SetHandler  perl-script
PerlHandler Apache::Registry
Options ExecCGI
PerlSendHeader On
</Location>

#
# set Apache::PerlRun Mode for /cgi-perl Alias
#
<Location /cgi-perl>
SetHandler  perl-script
PerlHandler Apache::PerlRun
Options ExecCGI
PerlSendHeader On
</Location>

</IfModule>

Diese Einträge legen Aliase für die Modi Apache::Registry und Apache::PerlRun an. Der Unterschied zwischen den beiden Modi gestaltet sich folgendermaßen:

Apache::Registry

Alle Skripte werden kompiliert und dann in einem Cache gehalten. Jedes Skript wird als Inhalt einer Subroutine angelegt. Dies ist gut für die Performance, hat jedoch auch einen Nachteil: Die Skripte müssen sehr sauber programmiert sein, da Variablen und Subroutinen zwischen den Aufrufen erhalten bleiben. Das bedeutet, dass man Variablen selbst zurücksetzen muss, damit sie beim nächsten Aufruf erneut verwendet werden können. Speichert man beispielsweise in einem Skript für Online-Banking die Kreditkartennummer eines Kunden in einer Variable auf, so könnte diese Nummer wieder auftauchen, wenn der nächste Kunde die Anwendung benutzt und somit das gleiche Skript wieder aufruft.

Apache::PerlRun

Die Skripte werden für jede Anfrage neu kompiliert, sodass Variablen und Subroutinen zwischen den Aufrufen aus dem Namespace verschwinden. Der Namespace ist die Gesamtheit aller Variablennamen und Routinennamen, die zu einem bestimmten Zeitpunkt während der Existenz eines Skripts definiert sind. Mit Apache::PerlRun muss man deswegen nicht so genau auf saubere Programmierung achten, da alle Variablen beim Start des Skripts frisch initialisiert sind und keine Werte aus vorangegangenen Aufrufen mehr enthalten können. Dies geht natürlich zu Lasten der Geschwindigkeit, ist aber immer noch deutlich schneller als CGI, da man sich den Aufruf eines eigenen Prozesses für den Interpreter spart. Apache::PerlRun verhält sich ähnlich wie CGI.

15.9.7. mod_php4

PHP ist eine Programmiersprache, die speziell für den Einsatz mit Webservern entworfen wurde. Im Unterschied zu anderen Sprachen, deren Befehle in eigenständigen Dateien (Skripten) abgelegt werden, sind bei PHP die Befehle (ähnlich wie bei SSI) in eine HTML-Seite eingebettet. Der PHP-Interpreter verarbeitet die PHP-Befehle und bettet das Ergebnis der Verarbeitung in die HTML-Seite ein.

Die Homepage für PHP findet man unter http://www.php.net/. Eine deutschsprachige PHP-Seite findet man unter http://www.php-homepage.de/.

Das Paket mod_php4-core muss in jedem Fall installiert sein. Für Apache 2 wird zusätzlich Paket apache2-mod_php4.

15.9.8. mod_python

Python ist eine objektorientierte Programmiersprache mit einer sehr klaren und leserlichen Syntax. Etwas ungewöhnlich, aber nach einer kurzen Eingewöhnungsphase recht angenehm ist, dass die Struktur des Programms von der Einrückung abhängt. Blocks werden nicht über geschweifte Klammern (wie in C und Perl) oder andere Begrenzer (wie begin und end) definiert, sondern darüber, wie tief sie eingerückt sind. Installieren Sie Paket apache2-mod_python.

Mehr über die Sprache findet man unter http://www.python.org/. Mehr Informationen über mod_python bietet http://www.modpython.org/.

15.9.9. mod_ruby

Ruby ist eine relativ junge objektorientierte High-Level-Programmiersprache, die sowohl Ähnlichkeit mit Perl als auch mit Python hat und die sich hervoragend für Skripte eignet. Mit Python verbindet sie die saubere, sehr übersichtliche Syntax, während sie von Perl die von vielen Programmierern geliebten (und von anderen verachteten) Kürzel wie zum Beispiel $.r, die Nummer der zuletzt aus der Eingabedatei gelesenen Zeile, übernommen hat. Von der grundlegenden Konzeption erinnert Ruby stark an Smalltalk.

Die Homepage von Ruby ist http://www.ruby-lang.org/. Auch für Ruby gibt es ein Apache-Modul, die Homepage findet sich unter http://www.modruby.net/.