PSR-16 & PSR-6 Cache implementations for WordPress transient and cache the OOP way
Version 2.0 is a BC breaks please read the following documentation
The best way to use this package is through Composer:
composer require italystrap/cacheThis package adheres to the SemVer specification and will be fully backward compatible between minor versions.
For more information about the WordPress API:
Initially I created this package to use the PSR-16 cache interface in WordPress, but starting from this issue #4 I decided to extract the drivers and also add the PSR-6 cache interface too.
From version 2.0 I also added the PSR-6 implementation, so you can also use the Pool class to cache your data if you need it.
So this package now support both the PSR-16 and PSR-6 cache interfaces.
The driver required by this package uses the Transients and Object Cache APIs from WordPress to store the data, but if you need to use other APIs, you can create your own driver because just implements the interface \ItalyStrap\Storage\CacheInterface from Storage API.
The first important thing is from the version 2 you need to pass the driver object and the expiration object to the constructor of the class you want to use.
SimpleCache and Pool are the two classes that need the driver and the expiration to be passed to the constructor.
The driver is an object wrapper for the WordPress Transient API and the WordPress Object Cache API.
The expiration object is used to set the expiration time of the cache.
Below in the documentation you will find the name of the drivers that you can use and the expiration object.
The second important thing is that the driver must implement the CacheInterface from Cache API, this way if you need to create your own driver you can do it simply by implementing the interface.
The expiration object is used to set the expiration time of the cache.
Because I want to be as close as possible to the PSR-16 and PSR-6 specifications, I have created an object that is responsible for setting the expiration time, this way I can reuse the same logic across all PSR-16 and PSR-6 implementations and I didn't need to create more methods that are not in the specifications.
Inside WordPress there are some constants that can be used to express time in seconds. Here is a list of them:
constMINUTE_IN_SECONDS = 60; // (seconds)constHOUR_IN_SECONDS = 60 * MINUTE_IN_SECONDS;
constDAY_IN_SECONDS = 24 * HOUR_IN_SECONDS;
constWEEK_IN_SECONDS = 7 * DAY_IN_SECONDS;
constMONTH_IN_SECONDS = 30 * DAY_IN_SECONDS;
constYEAR_IN_SECONDS = 365 * DAY_IN_SECONDS;Or you can use the built-in constant from ItalyStrap\Cache\ExpirationInterface:
useItalyStrap\Cache\ExpirationInterface;
$expirationTime = ExpirationInterface::MINUTE_IN_SECONDS;
$expirationTime = ExpirationInterface::HOUR_IN_SECONDS;
$expirationTime = ExpirationInterface::DAY_IN_SECONDS;
$expirationTime = ExpirationInterface::WEEK_IN_SECONDS;
$expirationTime = ExpirationInterface::MONTH_IN_SECONDS;
$expirationTime = ExpirationInterface::YEAR_IN_SECONDS;Or you can use the built-in PHP function strtotime() to express time in seconds.
if (false === ($special_data_to_save = \get_transient('special_data_to_save'))) {
// It wasn't there, so regenerate the data and save the transient$special_data_to_save = ['some-key' => 'come value'];
\set_transient('special_data_to_save', $special_data_to_save, 12 * HOUR_IN_SECONDS);
}The data you can save can be anything that is supported by the Serialization API. In short, you can save any scalar value, array, object.
useItalyStrap\Cache\Pool;
useItalyStrap\Cache\Expiration;
useItalyStrap\Storage\BinaryCacheDecorator;
useItalyStrap\Storage\Transient;
$driver = newBinaryCacheDecorator(newTransient()); // Or use new Cache()$expiration = newExpiration();
$pool = newPool($driver, $expiration);
// Pass the pool object to other classes that need to save data// then retrieve the data from the pool$item = $pool->getItem('special_data_to_save');
if (!$item->isHit()) {
// It wasn't there, so regenerate the data and save the transient$item->set(['some-key' => 'some value']);
$item->expiresAfter(12 * HOUR_IN_SECONDS);
$pool->save($item);
}
$special_data_to_save = $item->get();
['some-key' => 'some value'] === $special_data_to_save; // TrueOnly if you need to parse binary data (as for example image files) you can use the BinaryCacheDecorator class, but remember that if the file is more than 1MB it is better to not use this to save in the database.
And because you are a good developer, you will not save binary data in the database, and you will use the Transient class instead of the BinaryCacheDecorator class.
useItalyStrap\Cache\Expiration;
useItalyStrap\Cache\SimpleCache;
useItalyStrap\Storage\BinaryCacheDecorator;
useItalyStrap\Storage\Transient;
$driver = newBinaryCacheDecorator(newTransient()); // Or use new Cache()$expiration = newExpiration();
$cache = newSimpleCache($driver, $expiration);
// Pay attention to `SimpleCacheInterface::get()` method because if there is no value will return `null` and not `false` as the WordPress Transient API does.if (null === ($special_data_to_save = $cache->get('special_data_to_save'))) {
// It wasn't there, so regenerate the data and save the transient$special_data_to_save = ['some-key' => 'some value'];
$cache->set('special_data_to_save', $special_data_to_save, 12 * HOUR_IN_SECONDS);
}
['some-key' => 'some value'] === $special_data_to_save; // TrueuseItalyStrap\Cache\Pool;
useItalyStrap\Cache\Expiration;
useItalyStrap\Storage\BinaryCacheDecorator;
useItalyStrap\Storage\Transient;
$driver = newBinaryCacheDecorator(newTransient()); // Or use new Cache()$expiration = newExpiration();
$pool = newPool($driver, $expiration);
$item = $pool->getItem('special_data_to_save');
$item->set(['some-key' => 'some value']);
$item->expiresAfter(12 * HOUR_IN_SECONDS);
$pool->save($item);
$pool->deleteItem('special_data_to_save'); // Return bool// `::getItem()` will return a new item instance, always$pool->getItem('special_data_to_save')->isHit(); // Return falseuseItalyStrap\Cache\Expiration;
useItalyStrap\Cache\SimpleCache;
useItalyStrap\Storage\BinaryCacheDecorator;
useItalyStrap\Storage\Transient;
$driver = newBinaryCacheDecorator(newTransient()); // Or use new Cache()$expiration = newExpiration();
$cache = newSimpleCache($driver, $expiration);
$cache->set('special_data_to_save', ['some-key' => 'some value'], 12 * HOUR_IN_SECONDS);
$cache->delete('special_data_to_save'); // Return bool$cache->get('special_data_to_save'); // Return nulluseItalyStrap\Cache\Pool;
useItalyStrap\Cache\Expiration;
useItalyStrap\Storage\BinaryCacheDecorator;
useItalyStrap\Storage\Transient;
$driver = newBinaryCacheDecorator(newTransient()); // Or use new Cache()$expiration = newExpiration();
$pool = newPool($driver, $expiration);
$item = $pool->getItem('special_data_to_save');
$item->set(['some-key' => 'some value']);
$item->expiresAfter(12 * HOUR_IN_SECONDS);
$pool->save($item);
$pool->hasItem('special_data_to_save'); // Return true// But also this will return false if the item is expired or not exists$pool->hasItem('expired_or_not_existent_value'); // Return falseuseItalyStrap\Cache\Expiration;
useItalyStrap\Cache\SimpleCache;
useItalyStrap\Storage\BinaryCacheDecorator;
useItalyStrap\Storage\Transient;
$driver = newBinaryCacheDecorator(newTransient()); // Or use new Cache()$expiration = newExpiration();
$cache = newSimpleCache($driver, $expiration);
$cache->set('special_data_to_save', ['some-key' => 'some value'], 12 * HOUR_IN_SECONDS);
$cache->has('special_data_to_save'); // Return true// But also this will return false if the item is expired or not exists$cache->has('expired_or_not_existent_value'); // Return falseuseItalyStrap\Cache\Expiration;
useItalyStrap\Cache\SimpleCache;
useItalyStrap\Storage\BinaryCacheDecorator;
useItalyStrap\Storage\Transient;
$driver = newBinaryCacheDecorator(newTransient()); // Or use new Cache()$expiration = newExpiration();
$cache = newSimpleCache($driver, $expiration);
$values = [
'key' => 'value',
'key2' => 'value2',
];
$cache->setMultiple($values, 12 * HOUR_IN_SECONDS); // Return booluseItalyStrap\Cache\Expiration;
useItalyStrap\Cache\SimpleCache;
useItalyStrap\Storage\BinaryCacheDecorator;
useItalyStrap\Storage\Transient;
$driver = newBinaryCacheDecorator(newTransient()); // Or use new Cache()$expiration = newExpiration();
$cache = newSimpleCache($driver, $expiration);
$values = [
'key' => 'value',
'key2' => 'value2',
'key3' => false, // This will be replaced with 'some default value' because the method pass a default value
];
$fetched_values = $cache->getMultiple(\array_keys($values), 'some default value'); // Return valuesuseItalyStrap\Cache\Expiration;
useItalyStrap\Cache\SimpleCache;
useItalyStrap\Storage\BinaryCacheDecorator;
useItalyStrap\Storage\Transient;
$driver = newBinaryCacheDecorator(newTransient()); // Or use new Cache()$expiration = newExpiration();
$cache = newSimpleCache($driver, $expiration);
$values = [
'key' => 'value',
'key2' => 'value2',
'key3' => false,
];
$cache->deleteMultiple(\array_keys($values)); // Return boolThis method do not clear the entire WordPress cache, only the cache used by client with ::set() and ::setMultiple() methods.
useItalyStrap\Cache\Expiration;
useItalyStrap\Cache\SimpleCache;
useItalyStrap\Storage\BinaryCacheDecorator;
useItalyStrap\Storage\Transient;
$driver = newBinaryCacheDecorator(newTransient()); // Or use new Cache()$expiration = newExpiration();
$cache = newSimpleCache($driver, $expiration);
$cache->set('special_data_to_save',['some-key' => 'come value'], 12 * HOUR_IN_SECONDS);
$values = [
'key' => 'value',
'key2' => 'value2',
];
$cache->setMultiple($values, 12 * HOUR_IN_SECONDS);
$cache->clear(); // Return bool$cache->get('special_data_to_save'); // Return null$cache->get('key'); // Return null$cache->get('key2'); // Return nullCache::clear() will flush 'special_data_to_save', 'key' and 'key2'.
useItalyStrap\Cache\Expiration;
useItalyStrap\Cache\SimpleCache;
useItalyStrap\Storage\BinaryCacheDecorator;
useItalyStrap\Storage\Transient;
$driver = newBinaryCacheDecorator(newTransient()); // Or use new Cache()$expiration = newExpiration();
$cache = newSimpleCache($driver, $expiration);
// Get any existing copy of our transient dataif (false === ($special_data_to_save = $cache->get('special_data_to_save'))) {
// It wasn't there, so regenerate the data and save the transient$cache->set('special_data_to_save', ['some-key' => 'some value'], 12 * HOUR_IN_SECONDS);
}
// Use the data like you would have normally...//Or// Get any existing copy of our transient dataif (!$cache->has('special_data_to_save')) {
// It wasn't there, so regenerate the data and save the transient$cache->set('special_data_to_save', ['some-key' => 'some value'], 12 * HOUR_IN_SECONDS);
}
// Use the data like you would have normally...You could also use a Bridge to use the \Psr\SimpleCache\CacheInterface and inject the \Psr\Cache\CacheItemPoolInterface
useItalyStrap\Cache\Pool;
useItalyStrap\Cache\Expiration;
useItalyStrap\Storage\BinaryCacheDecorator;
useItalyStrap\Storage\Transient;
$driver = newBinaryCacheDecorator(newTransient()); // Or use new Cache()$expiration = newExpiration();
$pool = newPool($driver, $expiration);
$cache = new \ItalyStrap\Cache\SimpleCacheBridge($pool);
// and use the $cache as \Psr\SimpleCache\CacheInterfaceuseItalyStrap\Cache\Factory;
$cache = (newFactory())->makePool();
$cache = (newFactory())->makePoolTransient();
$cache = (newFactory())->makeSimpleCache();
$cache = (newFactory())->makeSimpleCacheTransient();
$cache = (newFactory())->makeSimpleCacheBridge();
$cache = (newFactory())->makeSimpleCacheBridgeTransient();All feedback / bug reports / pull requests are welcome.
Copyright (c) 2019 Enea Overclokk, ItalyStrap
This code is licensed under the MIT.