Caching
Tempest comes with a simple wrapper around PSR-6, which means you can use all PSR-6 compliant cache pools. Tempest uses Symfony's Cache Component as a default implementation, so all of Symfony's adapters are available out of the box.
Configuration
Tempest will use file caching by default. You can however configure another adapter via CacheConfig
:
// app/Config/cache.config.php use Tempest\Cache\CacheConfig; use Symfony\Component\Cache\Adapter\FilesystemAdapter; return new CacheConfig( pool: new FilesystemAdapter( namespace: '', defaultLifetime: 0, directory: __DIR__ . '/../../../../.cache', ), );
Caching
To be able to cache stuff, you need to inject the Cache
interface wherever you need it, and you're ready to go:
// app/RssController.php use Tempest\Cache\Cache; use Tempest\Http\Response; final readonly class RssController { public function __construct( private Cache $cache ) {} public function __invoke(): Response { $rss = $this->cache->resolve( key: 'rss', cache: function () { return file_get_contents('https://stitcher.io/rss') }, expiresAt: (new DateTimeImmutable())->add(new DateInterval('P1D')) ) } }
If you need more fine-grained control, the Cache
interface has the following methods:
-
resolve(string $key, Closure $cache, ?DateTimeInterface $expiresAt = null): mixed
— to retrieve an item from cache, it'll be cached automatically if it wasn't yet. -
put(string $key, mixed $value, ?DateTimeInterface $expiresAt = null): CacheItemInterface
— to get an item from cache. Note that this method will always returnCacheItemInterface
, even if there wasn't a hit (thanks PSR-6!). Use$item->isHit()
to know whether it's valid or not. -
get(string $key): mixed
— get an item from cache, returnsnull
if there wasn't a hit. -
remove(string $key): void
— removes an item from cache. -
clear(): void
— clears the cache in full.
Custom caches
It's important to note that the pool configured in CacheConfig
is used for the default cache, also known as the project cache. If needed, you can create your own caches with different adapters like so:
// app/RedisCache.php use Tempest\Container\Singleton; use Tempest\Cache\Cache; use Tempest\Cache\IsCache; use Psr\Cache\CacheItemPoolInterface; use Symfony\Component\Cache\Adapter\RedisAdapter; #[Singleton] final readonly class RedisCache implements Cache { use IsCache; protected function getCachePool(): CacheItemPoolInterface { return new RedisAdapter(/* … */) } }
In fact, Tempest comes with two other internal caches besides the project cache: ViewCache
and DiscoveryCache
. Both caches are used for internally by the framework, but can of course be cleared by users as well.
Clearing caches
Tempest comes with a cache:clear
command which allows you to pick which caches you want to clear:
./tempest cache:clear Which caches do you want to clear? > [ ] Tempest\Core\DiscoveryCache [ ] Tempest\Core\ConfigCache [ ] Tempest\View\ViewCache [ ] Tempest\Cache\ProjectCache [ ] …
If you want to clear all caches, you can use the --all
flag:
./tempest cache:clear --all Tempest\Core\DiscoveryCache cleared successfully Tempest\Core\ConfigCache cleared successfully Tempest\View\ViewCache cleared successfully Tempest\Cache\ProjectCache cleared successfully … cleared successfully Done
It's recommended that you clear all caches on deployment.
Enabling or disabling caches
It's likely that you don't want caches enabled in your local environment. Tempest comes with a couple of environment flags to manage whether caching is enabled or not. If you want to enable or disable all caches at once, you can use the CACHE
environment variable:
CACHE=true
If, however, you need more fine-grained control over which caches are enabled or not, you can use the individual environment toggles. Note that, in order for these to work, the CACHE
must be set to null
!
# The CACHE key is used as a global override to turn all caches on or off # Should be true in production, but null or false in local development CACHE=null # Enable or disable discovery cache DISCOVERY_CACHE=false # Enable or disable config cache CONFIG_CACHE=false # Enable or disable view cache VIEW_CACHE=false # Enable or disable project cache (allround cache) PROJECT_CACHE=false
It's recommended to always set CACHE=true
in production.
Finally, you can use the cache:status
command to verify which cashes are enabled and which are not:
./tempest cache:status Tempest\Core\DiscoveryCache enabled Tempest\Core\ConfigCache enabled Tempest\View\ViewCache disabled Tempest\Cache\ProjectCache disabled