RobotLoader: autoloading de clase
RobotLoader este un instrument care vă asigură confortul încărcării automate a claselor pentru întreaga dvs. aplicație, inclusiv bibliotecile terțe.
- scăpăm de toate
require
-urile - se vor încărca doar scripturile necesare
- nu necesită convenții stricte de denumire a directoarelor sau fișierelor
- extrem de rapid
- nicio actualizare manuală a cache-ului, totul se întâmplă automat
- bibliotecă matură, stabilă și utilizată pe scară largă
Putem deci uita de aceste blocuri de cod cunoscute:
require_once 'Utils/Page.php';
require_once 'Utils/Style.php';
require_once 'Utils/Paginator.php';
// ...
Instalare
Puteți descărca RobotLoader ca un singur fișier independent
RobotLoader.php
, pe care îl includeți folosind require
în scriptul dvs. și aveți imediat la
dispoziție autoloading confortabil pentru întreaga aplicație.
require '/path/to/RobotLoader.php';
$loader = new Nette\Loaders\RobotLoader;
// ...
Dacă construiți o aplicație folosind Composer, îl puteți instala folosind acesta:
composer require nette/robot-loader
Utilizare
Similar cu modul în care robotul Google parcurge și indexează paginile web, și RobotLoader parcurge toate scripturile PHP și înregistrează ce clase, interfețe, trait-uri și enumuri a găsit în ele. Rezultatele cercetării le stochează apoi în cache și le utilizează la următoarea cerere. Este suficient deci să specificați ce directoare trebuie să parcurgă și unde să stocheze cache-ul:
$loader = new Nette\Loaders\RobotLoader;
// directoarele pe care RobotLoader trebuie să le indexeze (inclusiv subdirectoarele)
$loader->addDirectory(__DIR__ . '/app');
$loader->addDirectory(__DIR__ . '/libs');
// setăm stocarea în cache în directorul 'temp'
$loader->setTempDirectory(__DIR__ . '/temp');
$loader->register(); // pornim RobotLoader
Și asta e tot, de acum înainte nu mai trebuie să folosim require
. Super!
Dacă RobotLoader întâlnește un nume de clasă duplicat în timpul indexării, va arunca o excepție și vă va informa despre aceasta. RobotLoader actualizează, de asemenea, automat cache-ul atunci când trebuie să încarce o clasă pe care nu o cunoaște. Vă recomandăm să dezactivați acest lucru pe serverele de producție, vezi Stocarea în cache.
Dacă doriți ca RobotLoader să sară peste anumite directoare, utilizați $loader->excludeDirectory('temp')
(poate fi apelat de mai multe ori sau puteți transmite mai multe directoare).
În mod implicit, RobotLoader raportează erorile din fișierele PHP aruncând excepția ParseError
. Acest lucru
poate fi suprimat folosind $loader->reportParseErrors(false)
.
Aplicație Nette
În interiorul unei aplicații Nette, unde se utilizează obiectul $configurator
în fișierul de pornire
Bootstrap.php
, scrierea poate fi simplificată:
$configurator = new Nette\Bootstrap\Configurator;
// ...
$configurator->setTempDirectory(__DIR__ . '/../temp');
$configurator->createRobotLoader()
->addDirectory(__DIR__)
->addDirectory(__DIR__ . '/../libs')
->register();
Analizator de fișiere PHP
RobotLoader poate fi utilizat și pur pentru a căuta clase, interfețe, trait-uri și enumuri în fișiere PHP fără a utiliza funcția de autoloading:
$loader = new Nette\Loaders\RobotLoader;
$loader->addDirectory(__DIR__ . '/app');
// scanează directoarele pentru clase / interfețe / trait-uri / enumuri
$loader->rebuild();
// returnează un array de perechi clasă => nume fișier
$res = $loader->getIndexedClasses();
Chiar și într-o astfel de utilizare, puteți folosi cache-ul. Datorită acestui fapt, la o nouă scanare, fișierele nemodificate nu vor fi analizate din nou:
$loader = new Nette\Loaders\RobotLoader;
$loader->addDirectory(__DIR__ . '/app');
// setăm stocarea în cache în directorul 'temp'
$loader->setTempDirectory(__DIR__ . '/temp');
// scanează directoarele folosind cache-ul
$loader->refresh();
// returnează un array de perechi clasă => nume fișier
$res = $loader->getIndexedClasses();
Stocarea în cache
RobotLoader este foarte rapid, deoarece utilizează inteligent cache-ul.
În timpul dezvoltării, practic nu vă dați seama că rulează în fundal. Își actualizează continuu cache-ul, deoarece ia în considerare faptul că clasele și fișierele pot apărea, dispărea, pot fi redenumite etc. Și nu scanează în mod repetat fișierele care nu s-au schimbat.
La implementarea pe un server de producție, dimpotrivă, recomandăm dezactivarea actualizării cache-ului folosind
$loader->setAutoRefresh(false)
(în aplicația Nette acest lucru se întâmplă automat), deoarece fișierele nu
se schimbă. În același timp, este necesar să ștergeți cache-ul la încărcarea unei noi versiuni pe hosting.
Scanarea inițială a fișierelor, când cache-ul nu există încă, poate dura, desigur, puțin timp pentru aplicațiile mai mari. RobotLoader are încorporată prevenirea cache stampede. Este o situație în care un număr mai mare de cereri concurente ajung pe serverul de producție, care pornesc RobotLoader, și deoarece cache-ul nu există încă, toate ar începe să scaneze fișierele. Ceea ce ar suprasolicita nejustificat serverul. Din fericire, RobotLoader funcționează astfel încât, în cazul mai multor cereri concurente, doar primul fir indexează fișierele, creează cache-ul, celelalte așteaptă și apoi utilizează cache-ul.
PSR-4
Astăzi, se poate utiliza Composer pentru
autoloading respectând PSR-4. Simplificat, este un sistem în care spațiile de nume și numele claselor corespund
structurii directoarelor și numelor fișierelor, adică, de exemplu, App\Core\RouterFactory
va fi în fișierul
/path/to/App/Core/RouterFactory.php
.
RobotLoader nu este legat de nicio structură fixă, de aceea este util în situațiile în care nu vă convine complet să aveți o structură de directoare proiectată la fel ca spațiile de nume în PHP, sau când dezvoltați o aplicație care, din punct de vedere istoric, nu utilizează astfel de convenții. Este posibil, de asemenea, să utilizați ambii loaderi împreună.