SELFHTML: Perl / Funktionsreferenz / Funktionen für Module und Packages
Author: Redaktion SELFHTML, selfhtml81@selfhtml.org
Description: Welche Funktionen es in Perl gibt, um Module einzubinden.
Keywords: SELFHTML, Perl, Funktionen, Perl-Funktionen, Module, Packages, package, require, use, @INC, %INC
Date: 2005-11-09T00:29:27+01:00

| # Funktionen für Module und Packages
| Allgemeines zu diesen Funktionen package - Namensraum eines Packages aktivieren require - andere Perl-Datei ausführen use - Modul einbinden

## Allgemeines zu diesen Funktionen

Um die hier beschriebenen Funktionen besser zu verstehen, sollten Sie das Kapitel über Perl-Module lesen.

### `@INC` - die Liste der Pfadnamen für Module

Wenn Sie mit require oder use eine Moduldatei (Dateien `*.pm`) einbinden, sucht Perl die entsprechende Datei entweder im aktuellen Verzeichnis, oder in einem Verzeichnis, das in der Liste für Modulpfadnamen gespeichert ist. Dazu dient die vordefinierte Variable `@INC`. Im Abschnitt Speicherorte für Module und die Liste @INC finden Sie ein Beispielscript, mit dessen Hilfe Sie sich den Inhalt von `@INC` ausgeben lassen können, um die bei Ihnen gültigen Pfade herauszufinden.

Neben der Liste `@INC` gibt es übrigens auch einen Hash namens `%INC`. In diesem Hash werden alle bereits geladenen Module gespeichert. Perl verhindert auf diese Weise, dass Module mehrfach geladen werden und dadurch zu unerwünschtem Verhalten im Programmablauf führen. Über derartige Probleme, die in C durch Präprozessoranweisungen wie `#ifndef` und `#define` gelöst werden müssen, brauchen Sie sich in Perl also keine Gedanken machen.

### Namensräume

Ein Namensraum heißt in Perl Package. Wenn Sie nichts anderes angeben, befindet sich jede Perl-Datei im package mit dem Namen `main`. Variablen, die innerhalb einer Perl-Datei ohne weitere Einschränkungen wie local oder my definiert werden, Namen von Subroutinen usw. gelten global in dieser einen Datei. Mit Hilfe der Funktion package können Sie eine Perl-Datei in mehrere Packages unterteilen.

### Was ist besser - `require` oder `use`?

Die beiden Funktionen require und use haben ähnliche Aufgaben, unterscheiden sich jedoch in ihrer Wirkungsweise. `require` wird zur Laufzeit eines Scripts geladen (und zwar an der Stelle, wo die `require`-Anweisung steht), während `use` bereits vorher, zur Kompilierzeit des Scripts, mit eingebunden wird. Bei `require` wechseln Sie also einfach während der Scriptausführung in ein anderes Script, lassen dieses kompilieren und ausführen, und kehren dann zurück. Bei `use` dagegen haben Sie nach dem Kompilieren, das Perl vor jedem Ausführen des Scripts durchführt, praktisch ein großes Script, dessen Code sich aus den Sourcen mehrerer Moduldateien zusammensetzt. Das hat Folgen. So werden Syntaxfehler, die in einem mit `use` eingebundenen Modul enthalten sind, bereits im Vorfeld erkannt, und das Script wird gar nicht erst ausgeführt. Bei `require` hingegen kann es passieren, dass das Hauptscript fehlerfrei ist, das eingebundene Script jedoch Syntaxfehler enthält. Diese werden jedoch erst erkannt, wenn das Hauptscript bereits läuft. Dadurch können undefinierte Zustände entstehen. Aus heutiger Sicht ist die Verwendung von `use` in den meisten Fällen vorzuziehen. Allerdings gibt es auch Ausnahmen.

Letztlich ist die Tatsache, dass es heute beide Funktionen gibt, historisch bedingt. `require` ist älter (wurde schon von Perl 4 interpretiert), während `use` seit Version 5 zur Verfügung steht. In der 5er-Version wurde das Modulkonzept von Perl stark erweitert und hat erst dort die heute verbreitete Form angenommen.

## package - Namensraum eines Packages aktivieren

Mit dieser Funktion bestimmen Sie einen Namensraum als den aktiv gültigen. Der Namensraum bleibt solange aktiv, bis mit einem neuen Aufruf von `package` ein anderer Namensraum aktiv wird, oder bis die natürliche Grenze eines Namensraums, also der aktuelle Block (etwa eine Subroutine) oder das Dateiende erreicht ist. Auf diese Weise können Sie innerhalb einer Scriptdatei modular arbeiten.

Erwartet als Parameter:
1. den Namen des Namensraums, oder eine Zahl, die als Versionsnummer interpretiert wird.

### Beispiel eines vollständigen CGI-Scripts in Perl:

Anzeigebeispiel: So sieht's aus (Zum Aufruf des Scripts ist eine Internet-Verbindung erforderlich)

    #!/usr/bin/perl -w

    use strict;
    use CGI::Carp qw(fatalsToBrowser);

    print "Content-type: text/html\n\n";
    print '<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN">', "\n";
    print "<html><head><title>Testausgabe</title>\n";
    print "</head><body>\n";

    package deutsch;
    use vars qw($Hauptstadt $Flaeche);
    $Hauptstadt = "Berlin";
    $Flaeche = "356.910 qm";

    package franzoesisch;
    use vars qw($Hauptstadt $Flaeche);
    $Hauptstadt = "Paris";
    $Flaeche = "551.500 qm";

    package deutsch;
    print "<p>Die Hauptstadt ist $Hauptstadt und das Land ist $Flaeche gross</p>";

    package franzoesisch;
    print "<p>Die Hauptstadt ist $Hauptstadt und das Land ist $Flaeche gross</p>";

    print "</body></html>\n";

### Erläuterung:

Das Beispiel ruft insgesamt vier mal `package` auf. Beim ersten mal wird dabei ein neuer Namensraum namens `deutsch` geschaffen, beim zweiten mal ein neuer Namensraum namens `franzoesisch`. Beim dritten mal wird der Namensraum `deutsch` erneut aufgerufen, und ab diesem Befehl kennt das Script nur diejenigen Variablen, Subroutinen usw., die innerhalb des gleichen Namensraums definiert wurden. Ebenso ist es beim vierten mal, wo der Namensraum `franzoesisch` wieder aufgerufen wird.

Bei Verwendung von `use strict` wie im Beispiel müssen die Variablen, die in den beiden ersten Package-Blöcken deklariert werden, allerdings explizit global deklariert werden, um bei späteren Aufrufen des Packages zur Verfügung zu stehen. Um die Deklaration globaler Variablen zu ermöglichen, steht das Standardmodul `vars` zur Verfügung. Im Beispiel sehen Sie, wie dieses Modul eingesetzt wird. Innerhalb eines Packages mit `use` eingebunden, stehen in der Klammer hinter `qw` alle Variablennamen des aktuellen Packages, die global, also ohne `my` davor deklariert werden sollen. Perl meckert dann trotz `use strict` nicht an den Deklarationen.

### Beachten Sie

Solange nicht mit `package` ein spezieller Namensraum aktiviert wird, gilt der Default-Namensraum von Perl, der den Namen `main` hat.

## require - andere Perl-Datei ausführen

Mit dieser Funktion führen Sie eine beliebige andere Perl-Datei aus. Das andere Script wird an der Stelle, an der der `require`-Aufruf steht, ausgeführt.

Erwartet als Parameter:
1. den Namen der einzubindenden Datei, gegebenenfalls mit Pfadnamen (Normalfall), oder eine Zahl, die als Versionsnummer interpretiert wird.

### Beispiel - Teil 1 (vollständiges CGI-Script in Perl):

Anzeigebeispiel: So sieht's aus (Zum Aufruf des Scripts ist eine Internet-Verbindung erforderlich)

    #!/usr/bin/perl -w

    use strict;
    use CGI::Carp qw(fatalsToBrowser);

    print "Content-type: text/html\n\n";
    print '<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN">', "\n";
    print "<html><head><title>Testausgabe</title>\n";
    print "</head><body>\n";

    require "hallo_welt.pl";

    print "</body></html>\n";

### Beispiel - Teil 2 (Moduldatei hallo_welt.pl):

    print "Hallo Welt!";
    1;

### Erläuterung:

Das Beispiel zeigt, wie Sie ein "herkömmliches" Perl-Script, das seinen Output auf die Standardausgabe schreibt, in ein CGI-Script einbetten können, sodass der Output an den aufrufenden Browser gesendet werden kann. Im GGI-Script wird mit `require "hallo_welt.pl"` eine andere Perl-Datei eingebunden. Diese Datei schreibt einfach ein `Hallo Welt` auf die Standardausgabe. Da es jedoch in ein Script eingebunden ist, das zuvor den üblichen HTTP-Header sendet, gelangt der Output als HTML-Inhalt zum Browser.

### Beachten Sie

Sie können mit `require` ebenso wie mit use eine Moduldatei mit der Endung `.pm` einbinden. In diesem Fall müssen Sie `require Modulname` angeben. Perl sucht dann nach einer Datei namens `Modulname.pm`. Auch die Syntax mit `::` ist genauso möglich wie bei `use` (vergleiche dazu den Abschnitt Adressierungs-Syntax beim Einbinden von Modulen).

Eingebundene Perl-Dateien müssen am Ende so etwas wie `1;` enthalten. Dadurch wird sichergestellt, dass das Modul oder die Modul-Funktion korrekt ausgeführt wird.

Wenn eine eingebundene Datei Subroutinen enthält, können Sie diese so aufrufen, als wären sie im aktuellen Perl-Script notiert.

## use - Modul einbinden

Mit dieser Funktion laden Sie ein Perl-Modul oder bestimmte Funktionen aus einem solchen Modul in ihr Script und können den entsprechenden Perl-Code in Ihrem Script benutzen.

Erwartet als Parameter:
1. den Namen des Moduls (Normalfall), oder eine Zahl, die als Versionsnummer interpretiert wird.
2. bis n. (optional) weitere, einschränkende Angaben (siehe weiter unten).

### Beispiel - Teil 1 (vollständiges CGI-Script in Perl):

Anzeigebeispiel: So sieht's aus (Zum Aufruf des Scripts ist eine Internet-Verbindung erforderlich)

    #!/usr/bin/perl -w

    use strict;
    use CGI::Carp qw(fatalsToBrowser);

    print "Content-type: text/html\n\n";
    print '<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN">', "\n";
    print "<html><head><title>Testausgabe</title>\n";
    print "</head><body>\n";

    use Syntax;
    my $Output = html_syntax("<h1>So sieht es aus</h1>","red");
    print "<h1>So sieht es aus</h1>\n";
    print "$Output\n";

    print "</body></html>\n";

### Beispiel - Teil 2 (Moduldatei Syntax.pm):

    package Syntax;
    use strict;
    use vars qw($VERSION @ISA @EXPORT);
    require Exporter;
    @ISA = qw(Exporter);
    @EXPORT = qw(html_syntax);
    $VERSION = 1.0;

    sub html_syntax {
      my $htmlstr = shift;
      my $color = shift;
      $htmlstr =~ s/\&/&amp;/g;
      $htmlstr =~ s/\"/&quot;/g;
      $htmlstr =~ s/\</&lt;/g;
      $htmlstr =~ s/\>/&gt;/g;
      $htmlstr =~ s/(&lt;)/<span style=\"color:$color\">$1/g;
      $htmlstr =~ s/(&gt;)/$1<\/span>/g;
      return($htmlstr);
    }
    1;

### Erläuterung:

Das Komplettbeispiel zeigt ein CGI-Script, in dem ein selbst definiertes Modul verwendet wird, sowie den Code der entsprechenden Moduldatei. Im CGI-Script wird die Moduldatei, die im Beispiel `Syntax.pm` heißt und im gleichen Verzeichnis wie das CGI-Script oder im Hauptverzeichnis von `@INC` abgelegt wird, mit `use Syntax;` eingebunden (vergleichen Sie dazu den Abschnitt Adressierungs-Syntax beim Einbinden von Modulen).

Das Hauptprogramm ruft dann eine Subroutine namens `html_syntax()` auf und übergibt ihr zwei Parameter, nämlich eine Zeichenkette mit HTML-Code und den Namen einer Farbe (`red`). Die Subroutine `html_syntax()` hat die Aufgabe, den übergebenen HTML-Code HTML-gerecht zu maskieren und die HTML-Tags in der angegebenen Farbe auszuzeichnen (also praktisch aus dem übergebenen HTML-Code den Code mit HTML-Syntax-Highlighting darstellbar zu machen). Die Subroutine erzeugt dabei neuen HTML-Code und gibt diesen am Ende zurück. Im Hauptprogramm wird der zurückgegebene Code in der Variablen `$Output` aufgefangen. Deren Inhalt kann schließlich an den Webserver zur Weitergabe an einen aufrufenden Browser ausgeliefert werden.

Die Subroutine `html_syntax()` ist im Modul `Syntax` mit `sub html_syntax` definiert. Die Moduldatei enthält zu Beginn noch einige weitere Anweisungen, auf die an dieser Stelle nicht näher eingegangen wird. Lesen Sie dazu den Abschnitt Erweiterte Verwendung von use (@EXPORT, @EXPORT_OK und qw).

Die folgende Tabelle zeigt, welche Varianten es gibt, um mit `use` ein Modul oder bestimmte Teile davon einzubinden:

Beispiel: | Erläuterung:
--- | ---
`use Beispiel;` | Bindet ein Modul namens `Beispiel.pm` ein, wobei diese Datei entweder im aktuellen Arbeitsverzeichnis oder in einem der Verzeichnisse abgelegt werden muss, die in @INC gespeichert sind. Geben Sie also den Dateinamen ohne die Endung an. Die Endung der Moduldatei muss `.pm` lauten.
`use Beispiel::Spezial;` | Bindet ein Modul namens `Spezial.pm` ein. Dabei löst Perl die `::`-Syntax als Pfadnamen auf - d.h. es wird eine Datei mit dem Pfadnamen `Beispiel/Spezial.pm` erwartet. Dies ist ein relativer Pfadname, ausgehend von einem der Verzeichnispfade, die in @INC gespeichert sind.
`use CGI::Carp qw(fatalsToBrowser);` | Bindet aus dem Verzeichnis `CGI` das Modul `Carp.pm` ein. Das Symbol `fatalsToBrowser` wird der Importliste übergeben. Normalerweise wird es dann in den aktuellen Namensraum importiert, was allerdings - typisch für Perl - gerade bei diesem populären Beispiel nicht der Fall ist. Die Übergabe von `fatalsToBrowser` löst hier eine Sonderbehandlung aus.
`use 5.003;` | Script läuft nur weiter, wenn ein Perl-Interpreter installiert ist, der eine Versionsnummer gleich oder höher als 5.003 hat.

### Beachten Sie

Die Anweisung:
`use Modulname;`
ist gleichbedeutend mit:
`BEGIN { require Modulname; import Modulname [Importliste]; }`
Die Funktion `use` leistet also die Summe aus dem, was die Funktion require in Verbindung mit der Methode `import` leistet.

Wenn Sie `use` genau ein Argument übergeben und dieses Argument eine Zahl ist, also z.B. `5` oder `5.003`, dann prüft Perl diese Angabe gegen die Versionsnummer des Perl-Interpreters. Ist die Versionsnummer des Perl-Interpreters niedriger als die angegebene Zahl, wird das laufende Script sofort mit einer Fehlermeldung beendet. Dies kann sinnvoll sein, um zu verhindern, dass ein Script weiterläuft, das Code enthält, der höhere Perl-Versionen erfordert.

Module müssen am Ende so etwas wie `1;` enthalten. Dadurch wird sichergestellt, dass das Modul korrekt eingebunden wird.

| Einführung in das Arbeiten mit Modulen
| Funktionen für Informationen aus Konfigurationsdateien

© 2007 Impressum