RobotLoader: Klasse Autoloading
RobotLoader ist ein Tool, das Ihnen den Komfort des automatischen Ladens von Klassen für Ihre gesamte Anwendung einschließlich der Bibliotheken von Drittanbietern bietet.
- Eliminieren Sie alle
require
Anweisungen - Nur notwendige Skripte werden geladen
- Erfordert keine strengen Namenskonventionen für Verzeichnisse oder Dateien
- Äußerst schnell
- Keine manuellen Cache-Updates, alles läuft automatisch ab
- Ausgereifte, stabile und weit verbreitete Bibliothek
Wir können also diese vertrauten Codeblöcke vergessen:
require_once 'Utils/Page.php';
require_once 'Utils/Style.php';
require_once 'Utils/Paginator.php';
//...
Einrichtung
Sie können RobotLoader als einzelne Standalone-Datei
RobotLoader.php
herunterladen, die Sie mit require
in Ihr Skript einbinden, und sofort das
komfortable automatische Laden für die gesamte Anwendung nutzen.
require '/path/to/RobotLoader.php';
$loader = new Nette\Loaders\RobotLoader;
//...
Wenn Sie eine Anwendung mit Composer erstellen, können Sie ihn über installieren:
composer require nette/robot-loader
Verwendung
Ähnlich wie der Google-Roboter Webseiten crawlt und indiziert, geht der RobotLoader durch alle PHP-Skripte und notiert, welche Klassen, Schnittstellen, Traits und Enums er gefunden hat. Anschließend speichert er die Ergebnisse im Cache, um sie bei nachfolgenden Anfragen zu verwenden. Sie müssen nur angeben, welche Verzeichnisse er durchsuchen soll und wo der Cache gespeichert werden soll:
$loader = new Nette\Loaders\RobotLoader;
// Verzeichnisse, die RobotLoader indizieren soll (einschließlich Unterverzeichnisse)
$loader->addDirectory(__DIR__ . '/app');
$loader->addDirectory(__DIR__ . '/libs');
// Zwischenspeicherung auf das Verzeichnis "temp" einstellen
$loader->setTempDirectory(__DIR__ . '/temp');
$loader->register(); // RobotLoader aktivieren
Und das war's, von nun an brauchen wir require
nicht mehr zu verwenden. Großartig!
Wenn RobotLoader während der Indizierung auf einen doppelten Klassennamen stößt, wird eine Ausnahme ausgelöst und Sie werden benachrichtigt. RobotLoader aktualisiert auch automatisch den Cache, wenn er eine unbekannte Klasse laden muss. Wir empfehlen, dies auf Produktionsservern zu deaktivieren, siehe Caching.
Wenn Sie möchten, dass RobotLoader bestimmte Verzeichnisse überspringt, verwenden Sie
$loader->excludeDirectory('temp')
(kann mehrfach aufgerufen werden oder mehrere Verzeichnisse übergeben).
Standardmäßig meldet RobotLoader Fehler in PHP-Dateien, indem er eine ParseError
Exception auslöst. Dies kann
mit $loader->reportParseErrors(false)
unterdrückt werden.
Nette Anwendung
Innerhalb von Nette Application, wo $configurator
in Bootstrap.php
verwendet wird, können Sie
RobotLoader auf diese Weise einrichten:
$configurator = new Nette\Bootstrap\Configurator;
//...
$configurator->setTempDirectory(__DIR__ . '/../temp');
$configurator->createRobotLoader()
->addDirectory(__DIR__)
->addDirectory(__DIR__ . '/../libs')
->register();
PHP-Dateianalysator
RobotLoader kann auch nur zum Auffinden von Klassen, Interfaces, Traits und Enums in PHP-Dateien ohne Verwendung der Autoloading-Funktion verwendet werden:
$loader = new Nette\Loaders\RobotLoader;
$loader->addDirectory(__DIR__ . '/app');
// Durchsucht Verzeichnisse nach Klassen/Schnittstellen/Traits/Enums
$loader->rebuild();
// Gibt ein Array von Klasse => Dateinamenpaaren zurück
$res = $loader->getIndexedClasses();
Auch bei einer solchen Verwendung können Sie das Caching nutzen. Dadurch wird sichergestellt, dass unveränderte Dateien nicht erneut gescannt werden:
$loader = new Nette\Loaders\RobotLoader;
$loader->addDirectory(__DIR__ . '/app');
// Zwischenspeicherung auf das Verzeichnis 'temp' einstellen
$loader->setTempDirectory(__DIR__ . '/temp');
// Scannt Verzeichnisse unter Verwendung des Caches
$loader->refresh();
// Gibt ein Array von Klasse => Dateinamenpaaren zurück
$res = $loader->getIndexedClasses();
Zwischenspeichern
RobotLoader ist sehr schnell, weil er geschickt die Zwischenspeicherung nutzt.
Während der Entwicklung bemerken Sie kaum, dass er im Hintergrund läuft. Der Cache wird ständig aktualisiert, da Klassen und Dateien erstellt, gelöscht, umbenannt usw. werden können. Und er scannt unveränderte Dateien nicht erneut.
Auf einem Produktionsserver hingegen empfehlen wir, die Cache-Aktualisierung mit $loader->setAutoRefresh(false)
zu deaktivieren (in einer Nette-Anwendung geschieht dies automatisch), da sich die Dateien nicht ändern. Gleichzeitig ist es
notwendig, den Cache zu leeren, wenn eine neue Version zum Hosting hochgeladen wird.
Das anfängliche Scannen der Dateien, wenn der Cache noch nicht vorhanden ist, kann bei größeren Anwendungen natürlich einen Moment dauern. RobotLoader hat einen eingebauten Schutz gegen Cache-Stampede. Dies ist eine Situation, in der eine große Anzahl gleichzeitiger Anfragen auf einem Produktionsserver RobotLoader auslösen würde, und da der Cache noch nicht existiert, würden sie alle mit dem Scannen von Dateien beginnen, was den Server überlasten würde. Glücklicherweise arbeitet RobotLoader so, dass nur der erste Thread die Dateien indiziert und den Cache erstellt, während die anderen warten und dann den Cache verwenden.
PSR-4
Heutzutage können Sie Composer für das
automatische Laden unter Einhaltung von PSR-4 verwenden. Einfach ausgedrückt, handelt es sich um ein System, bei dem die
Namensräume und Klassennamen der Verzeichnisstruktur und den Dateinamen entsprechen, z. B. App\Core\RouterFactory
in
der Datei /path/to/App/Core/RouterFactory.php
.
RobotLoader ist nicht an eine feste Struktur gebunden, so dass es in Situationen nützlich ist, in denen Sie die Verzeichnisstruktur nicht genau wie die PHP-Namensräume gestalten wollen, oder wenn Sie eine Anwendung entwickeln, die historisch gesehen keine solchen Konventionen verwendet. Es ist auch möglich, beide Lader zusammen zu verwenden.