CacheManager

Der CacheManager kümmert sich um die Verwaltung und Initialisierung der CacheProvider, die sich letztlich um die Funktion des Lesens, Schreibens und Löschen von Cache-Inhalten kümmern. Im Release sind bereits wichtige Provider und eine abstrakte Definition zur Implementierung von eigenen Providern enthalten.

Als "Adresse" von Cache-Einträgen werden sogenannte CacheKeys eingesetzt. Dieses definieren einen beliebig komplexen Schlüssel, der für das Laden und Speichern von Objekten (einfache Zeichen, Objekte, Listen, ...) als eindeutiger Key gilt.

1. Konfiguration

Der CacheManager erwartet die Konfigurationsdatei cacheconfig.ini im Namespace APF\tools\cache. Für die Verwendung des CacheManagers ist jeweils eine minimale Sektion der Form

APF-Konfiguration
[my_cache_instance] Provider = "" Active = "" [ExpireTime = ]

notwendig. Der Provider definiert den voll-qualifizierten Klassen-Namen des zu verwendenden Cache-Providers. Die Direktive Active definiert, ob der Caching-Mechanismus aktiv ist oder nicht. Wenn die Direktive true beinhaltet befindet sich der CacheManager im Status aktiv.

Mit Hilfe der Direktive ExpireTime lässt sich die Gültigkeit von Cache-Elementen für die gewünschte Instanz definieren. Der Wert definiert die Lebensdauer in Sekunden.

Je nach Provider müssen weitere Parameter definiert werden. Diese können in den folgenden Kapiteln nachgelesen werden.

2. Anwendung

Da es möglich sein soll, mehrere Cache-Manager-Instanzen innerhalb einer Anwendung zu verwenden wurde eine Factory zur Erzeugung und Verwaltung der konkreten Instanzen eineführt. Diese besitzt die Methode getCacheManager() um einen für den gewünschten Anwendungsfall konfigurierten CacheManager zu erzeugen. Die CacheManagerFabric wird dabei als Singleton erzeugt um bei einem erneuten Aufruf der Komponente keinen Initialisierungsaufwand mehr betreiben zu müssen - Caching muss schließlich performant sein!

Die folgende Code-Box zeigt einen typischen Anwendungsfall des CacheManagers:

PHP-Code
use APF\tools\cache\CacheManagerFabric; use APF\tools\cache\key\SimpleCacheKey; $cMF = &$this->getServiceObject('APF\tools\cache\CacheManagerFabric'); $cM = &$cMF->getCacheManager('{config_section}'); $cacheKey = new SimpleCacheKey('my_cache_key'); $cacheContent = $cM->getFromCache($cacheKey); if($cacheContent === null){ $cacheContent = /* generate content */; $cM->writeToCache($cacheKey,$cacheContent); } // clear cache if necessary if(/* ... */){ if(/* ... */){ $cM->clearCache($cacheKey); // clean only the desired cache content } else{ $cM->clearCache(); // clean the entire namespace } }

Wie dem Beispiel bereits zu entnehmen ist, besitzt der CacheManager drei Methoden, die jeweils vom zuständigen Provider implementiert werden:

  • getFromCache(): Liest den gewünschten Cache-Inhalt. Ist für den Cache-Key noch kein Inhalt vorhanden, wird null zurückgegeben. Dies kann gleichzeitig als Indiz für das Neuanlegen des Cache-Inhalts verwendet werden.
  • writeToCache(): Schreibt den Inhalt unter dem konfigurierten Namespace und dem übergebenen Cache-Key in den Cache. Bei Erfolg wird true, bei einem Fehler false zurückgegeben.
  • clearCache(): Die Methode clearCache() dient zum Löschen des Caches. Hierbei können durch Übergabe des gewünschten Cache-Keys dieser selbst, oder ohne Argument, der komplette Namespace gelöscht werden.

3. Mitgelieferte Provider

Das Framework liefert bereits fertige Provider mit. Diese decken die typischen Anwendungsfälle ab. Sollte für einen definierten Anwendungsfall kein Provider enthalten sein, können diese wie in Kapitel 4 beschrieben erweitert werden.

Der AdvancedTextCacheProvider bildet dabei eine Erweiterung des TextCacheProvider und der AdvancedObjectCacheProvider erweitert den AdvancedTextCacheProvider um die Möglichkeit, beliebige Objekte im Cache zu speichern. Details können den Kapiteln 3.5 und 3.6 entnommen werden.

3.1. Text-Cache Provider

Der Text-Cache-Provider implementiert ein einfaches Filesystem-Caching. Hierbei wird unter einem definierten Basis-Pfad der gewünschte Cache-Inhalt strukturiert abgelegt. Als erstes Strukturelement wird der Namespace eingesetzt, gefolgt von einem weiteren Unterordner aus den ersten beiden Zeichen des md5-Schlüssels des Cache-Keys.

Um den Provider verwenden zu können, muss die referenzierte Konfigurationssektion wir folgt aufgebaut sein:

APF-Konfiguration
[text_cache] Provider = "APF\tools\cache\provider\TextCacheProvider" Active = "" BaseFolder = "" Namespace = "" [FolderPermission = "0770"]

BaseFolder beinhaltet den Pfad zum vom CacheManager verwalteten Ordner, das Attribut Namespace benennet das erste Strukturelement. Bitte beachten Sie, dass Abschnitte des Namespaces jeweils durch "\" getrennt notiert werden sollten.

Der Schlüssel FolderPermission ist optional und kann dazu genutzt werden, die Permission-Maske für angelegte Cache-Ordner zu definieren.

Ist der Parameter ExpireTime nicht gesetzt, wir dieser mit dem Wert 0 vorbelegt und die Einträge bis manuellen Löschen vorgehalten.
Der Text-Cache-Provider verwendet den FilesystemManager für die Verwaltung des Cache-Ordners. Aus diesem Grund muss der Benutzer, unter dem der Webserver läuft Schreibrechte für diesen Ordner besitzen.

Dieser Provider unterstützt Verwendung der Klasse SimpleCacheKey und AdvancedCacheKey zur Identifizierung eines Cache-Eintrags.

3.2. Objekt-Cache Provider

Der Objekt-Cache-Provider ist eine Erweiterung des unter 3.1. beschriebenen Text-Caches. Zur Ablage der Cache-Dateien wird ebenfalls ein Ordner auf dem Dateisystem verwendet. Der Unterschied besteht darin, dass die als Cache-Content übergebenen Werte serialisiert auf der Platte vorgehalten werden. Hierdurch ist es möglich, einen Filesystem-basierten Objekt-Cache aufzubauen.

Die Dafür notwendige Konfigurationssektion gestaltet sich wie folgt:

APF-Konfiguration
[object_cache] Provider = "APF\tools\cache\provider\ObjectCacheProvider" Active = "" BaseFolder = "" Namespace = "" [FolderPermission = "0770"]

Der Schlüssel FolderPermission ist optional und kann dazu genutzt werden, die Permission-Maske für angelegte Cache-Ordner zu definieren.

Ist der Parameter ExpireTime nicht gesetzt, wir dieser mit dem Wert 0 vorbelegt und die Einträge bis manuellen Löschen vorgehalten.

Dieser Provider unterstützt Verwendung der Klasse SimpleCacheKey und AdvancedCacheKey zur Identifizierung eines Cache-Eintrags.

3.3. Mem-Cache Provider

Der Mem-Cache-Provider bietet die Möglichkeit, PHP-Objekte im memcached-Server vorzuhalten. Hierbei wird das jeweilige PHP-Objekt beim Schreiben des Caches serialisiert und beim Lesen deserialisiert. Bitte beachten Sie, dass hierdurch Objekt-Inhalte vom Typ Ressource verloren gehen und nach dem Deserialisieren neu initialisiert werden müssen.

Für den Zugriff auf einen memcached-Server ist folgende Konfiguration vorzuhalten:

APF-Konfiguration
[mem_cache] Provider = "APF\tools\cache\provider\MemCacheProvider" Active = "" Host = "" Port = "" PersistentConnect = "" Namespace = ""

Die Implementierung des MemCacheProviders beinhaltet - trotz der Tatsache, dass die memcache_*() keine Namespaces kennt - ebenfalls einen Namespace-Support. Dieser wird über ein Präfix im Cache-Key abgebildet. Damit ist es wie bei den bisherigen Provider-Implementierungen möglich, komplette Namespaces zu löschen.

Für den Einsatz des MemCacheProviders ist die PHP-Erweiterung memcache erforderlich!
Ist der Parameter ExpireTime nicht gesetzt, wir dieser mit dem Wert 0 vorbelegt und die Einträge bis zum Neustart des Memcacher-Servers vorgehalten.

Dieser Provider unterstützt die Verwendung der Klasse SimpleCacheKey zur Identifizierung eines Cache-Eintrags.

3.4. Datenbank-Cache Provider

Der DBCacheProvider nutzt eine Datenbank-Tabelle zur Ablage der Cache-Informationen. Um diesen nutzen zu können, muss folgende Konfiguration vorgehalten werden:

APF-Konfiguration
[database_cache] Provider = "APF\tools\cache\provider\DBCacheProvider" Active = "" Connection = "" Table = "" Namespace = ""

Connection beinhaltet den Connection-Key, der dazu verwendet wird um über den ConnectionManager eine Verbindung zu einer Datenbank zu erzeugen. Hierzu muss eine korrespondierende Datenbank-Verbindung wie in der Klassenreferenz aufgeührten Weise angelegt werden. Table definiert den Namen der Cache-Tabelle, die mit folgendem Statement erzeugt werden sollte:

SQL-Statement
CREATE TABLE `database_cache` ( `CacheID` int(5) NOT NULL auto_increment, `namespace` varchar(100) NOT NULL default '', `cachekey` varchar(100) NOT NULL default '', `value` text NOT NULL, PRIMARY KEY (`CacheID`), KEY `cachevalues` (`namespace`,`cachekey`) );
Bitte beachten Sie, dass die Benennung der Spalten namespace, cachekey und value bindend ist.

Dieser Provider unterstützt die Verwendung der Klasse SimpleCacheKey zur Identifizierung eines Cache-Eintrags.

3.5. Erweiterter Text-Cache Provider

Die Implementierung AdvancedTextCacheProvider unterstützt einen komplexeren Cache-Key und ist dazu gedacht Cache-Elemente zu speichern, die mehrere Ausprägungen haben. Dies ist beispielsweise bei einem HTML-Cache notwendig, der unterschiedliche Ergebnisse (z.B. unterschiedliche URLs) für die gleiche Seite abspeichern möchte. Dabei soll die Möglichkeit erhalten bleiben, die Inhalte einer bestimmten Seite teilweise oder komplett zu löschen.

Zur Verwendung des Providers ist folgende Konfigurations-Sektion notwendig:

APF-Konfiguration
Provider = "APF\tools\cache\provider\AdvancedTextCacheProvider" Active = "" BaseFolder = "" Namespace = "" [FolderPermission = "0770"]

Der Schlüssel FolderPermission ist optional und kann dazu genutzt werden, die Permission-Maske für angelegte Cache-Ordner zu definieren.

Ist der Parameter ExpireTime nicht gesetzt, wir dieser mit dem Wert 0 vorbelegt und die Einträge bis manuellen Löschen vorgehalten.

Um einen Cache-Eintrag zu lesen bzw. zu speichern, ist folgender PHP-Code notwendig:

PHP-Code
use APF\tools\cache\CacheManagerFabric; use APF\tools\cache\key\AdvancedCacheKey; $pageId = /* ... */; $currentUrl = $_SERVER['REQUEST_URI']; // create cache key, that stores the cache for one page but with different flavours $cacheKey = new AdvancedCacheKey($pageId, $currentUrl); // load cached content $content = $cM->getFromCache($cacheKey); if($content === null) { $cacheContent = /* generate content */; $cM->writeToCache($cacheKey, $cacheContent); } // clear cache if necessary if(/* ... */){ if(/* ... */){ $cM->clearCache($cacheKey); // clean only the desired cache content } else{ $cM->clearCache(); // clean the entire namespace } }

Dieser Provider unterstützt Verwendung der Klasse SimpleCacheKey und AdvancedCacheKey zur Identifizierung eines Cache-Eintrags.

3.6. Erweiterter Objekt-Cache Provider

Der AdvancedObjectCacheProvider erweitert den AdvancedTextCacheProvider um die Möglichkeit, serialisierte Objekte im Cache zu speichern. Die Struktur und Verwendung der Provider-Implementierung gestaltet sich identisch. Auch hier kommt die Klasse AdvancedCacheKey zum Einsatz.

Der Provider kann genutzt werden, wenn die Konfigurations-Sektion folgende Werte definiert:

APF-Konfiguration
Provider = "APF\tools\cache\provider\AdvancedObjectCacheProvider" Active = "" BaseFolder = "" Namespace = "" [FolderPermission = "0770"]

Der Schlüssel FolderPermission ist optional und kann dazu genutzt werden, die Permission-Maske für angelegte Cache-Ordner zu definieren.

Ist der Parameter ExpireTime nicht gesetzt, wir dieser mit dem Wert 0 vorbelegt und die Einträge bis manuellen Löschen vorgehalten.

Dieser Provider unterstützt Verwendung der Klasse SimpleCacheKey und AdvancedCacheKey zur Identifizierung eines Cache-Eintrags.

3.7. APC Cache-Provider

Mit Hilfe des ApcCacheProvider ist es möglich, Inhalte in einem APC Shared Memory Segment Request-übergreifend zu speichern.

Nutzen Sie den ApcCacheProvider um die Anzahl der I/O-Zugriffe ihrer Applikation zu verringern und dadurch die Anwendung zu beschleunigen.

Zur Verwendung des Providers ist folgende Konfigurations-Sektion notwendig:

APF-Konfiguration
Provider = "APF\tools\cache\provider\ApcCacheProvider" Active = "" Namespace = ""

Da der Cache im RAM des Webservers abgelegt ist, wird lediglich ein Namespace benötigt.

Ist der Parameter ExpireTime nicht gesetzt, wir dieser mit dem Wert 0 vorbelegt und die Einträge bis zum Neustart des Webservers vorgehalten.

Lesen, Speichern und Löschen eines Cache-Eintrags funktioniert identisch zu den bisher beschriebenen Providern.

Dieser Provider unterstützt Verwendung der Klasse SimpleCacheKey und AdvancedCacheKey zur Identifizierung eines Cache-Eintrags.

4. Gültigkeit von Cache-Einträgen

Mit Hilfe der Konfigurationsoption ExpireTime lässt sich die Gültigkeit von Cache-Einträgen begrenzen. Zusätzlich zur globalen Konfiguration der Gültigkeit kann diese auch pro Instanz des Cache-Keys festgelegt werden.

Hierzu stehen Ihnen optionale Argumente in den Konstruktoren von SimpleCacheKey und AdvancedCacheKey als auch die Methode setTtl() in beiden Klassen zur Verfügung.

Beabsichtigen Sie einen Cache-Eintrag mit einer bestimmten Lebensdauer als gültig zu akzeptieren, lässt sich dies wie folgt realisieren:

PHP-Code
use APF\tools\cache\CacheManagerFabric; use APF\tools\cache\key\SimpleCacheKey; $cMF = &$this->getServiceObject('APF\tools\cache\CacheManagerFabric'); $cM = &$cMF->getCacheManager('{config_section}'); $cacheKey = new SimpleCacheKey('my_cache_key', 3600); $cacheContent = $cM->getFromCache($cacheKey);

Sie erhalten nun nur dann ein Ergebnis von CacheManager::getFromCache(), sofern der Cache-Eintrag nicht älter als eine Stunde ist.

Bitte beachten Sie, dass eine explizite Gültigkeit im CacheKey die globale Konfiguration der gewünschten CacheManager-Instanz überschreibt. Sofern weder im CacheKey noch in der Konfiguration ein Wert definiert wurde, wird der Wert auf 0 (Null) gesetzt und der Cache-Eintrag für immer als gültig markiert.

Da die Definition der Gültigkeit im Interface CacheKey verankert ist, unterstützt sowohl der SimpleCacheKey als auch der AdvancedCacheKey die beschriebene Option.

5. Erweiterung

Die Implementierung des CacheManagers sieht mehrere Komponenten vor. Zur Erzeugung wird die CacheManagerFabric eingesetzt, die die konkreten CacheManager-Instanzen erzeugt, initialisiert und für die weitere Verwendung vorhält. Der CacheManager selbst übernimmt die Initialisierung der gewünschten Provider und bietet die in Kapitel 2 beschrieben Methoden. Jeder Provider implementiert dabei das Interface CacheProvider - genauer die Methoden read(), write() und clear().

Diesen wird jeweils der gewünschte Cache-Key und ggf. der zu schreibende Inhalt übergeben. Die Konfigurationsparameter stehen innerhalb der Methoden über die protected Funktion getConfigAttribute() zur Verfügung, die den Namen des Attributes erwartet. Hierzu ist es jedoch erforderlich, von der Klasse CacheBase zu erben. Zur Betriebssicherung wird eine Exception erzeugt, sollte die gewünschte Konfigurationsdirektive nicht vorhanden oder leer sein. Details zur Klassendefinition kann der API-Dokumentation unter Downloads entnommen werden.

Die Cache-Schlüssel werden durch eigene Daten-Typen abgebildet. Das Schema wird durch das Interface CacheKey vorgegeben. Im Release werden die Implementierungen SimpleCacheKey und AdvancedCacheKey mitgeliefert.

Da ein Cache-Provider über seinen Namespace und seinen Klassennamen adressiert wird, kann dieser in einem beliebigen Namespace (z.B. der Namespace der Applikation) abgelegt werden. Der Rumpf eines eigenen Providers gestaltet sich wie folgt:

PHP-Code
use APF\tools\cache\CacheBase; use APF\tools\cache\CacheProvider; class MyCacheProvider extends CacheBase implements CacheProvider { public function read(CacheKey $cacheKey){ } public function write(CacheKey $cacheKey, $object){ } public function clear(CacheKey $cacheKey = null){ } }

Die erwarteten Rückgabe-Werte sind der API-Dokumentation des Interface CacheProvider zu entnehmen. Sollen Funktionen der bestehenden Provider genutzt werden, besteht weiterhin die Mögichkeit von diesen abzuleiten. Dieses Mittel wird bereits intern für die Implementierung des ObjectCacheProvider genutzt, da dieser ebenso einen dedizierten Ordner für die Ablage der Objekt-Cache-Dateien nutzt.

Die folgende Code-Box zeigt die Implementierung eines Cache-Providers für das Cachen von Image-Ressourcen:

PHP-Code
use APF\tools\cache\provider\TextCacheProvider; use APF\tools\filesystem\FilesystemManager; class PNGImageCacheProvider extends TextCacheProvider { public function read(CacheKey $cacheKey){ $cacheFile = $this->getCacheFile($cacheKey); if(!file_exists($cacheFile)){ return null; } else{ return createimagefrompng($cacheFile); } } public function write(CacheKey $cacheKey, $object){ $cacheFile = $this->getCacheFile($cacheKey); FilesystemManager::createFolder(dirname($cacheFile)); imagepng($object,$cacheFile); } public function clear(CacheKey $cacheKey = null){ if($cacheKey === null){ $baseFolder = $this->getConfigAttribute('BaseFolder'); FilesystemManager::deleteFolder($baseFolder,true); } else{ $cacheFile = $this->getCacheFile($cacheKey); FilesystemManager::removeFile($cacheFile); } } }

Sofern die mitgelieferten Cache-Schlüssel nicht den Anforderungen des neu implementierten Providers genügen, kann dieser unter Einhaltung der Regeln des CacheKey-Interface erweitert werden. Hierzu stehen die Klassen SimpleCacheKey und AdvancedCacheKey als Vorlage zur Verfügung.

Kommentare

Möchten Sie den Artikel eine Anmerkung hinzufügen, oder haben Sie ergänzende Hinweise? Dann können Sie diese hier einfügen. Die bereits verfassten Anmerkungen und Kommentare finden Sie in der untenstehenden Liste.
Für diesen Artikel liegen aktuell keine Kommentare vor.