|
| 1 | +.. index:: |
| 2 | + single: Cache Pool |
| 3 | + single: APC Cache, APCu Cache |
| 4 | + single: Doctrine Cache |
| 5 | + single: Redis Cache |
| 6 | + |
| 7 | +Cache Pools |
| 8 | +=========== |
| 9 | + |
| 10 | +Cache Pools are the logical repositories of cache items. They perform all the |
| 11 | +common operations on items, such as saving them or looking for them. Cache pools |
| 12 | +are independent from the actual cache implementation. Therefore, applications |
| 13 | +can keep using the same cache pool even if the underlying cache mechanism |
| 14 | +changes from a file system based cache to a Redis or database based cache. |
| 15 | + |
| 16 | +Creating Cache Pools |
| 17 | +-------------------- |
| 18 | + |
| 19 | +Cache Pools are created through the **cache adapters**, which are classes that |
| 20 | +implement :class:`Symfony\\Component\\Cache\\Adapter\\AdapterInterface`. This |
| 21 | +component provides several adapters ready to use in your applications. |
| 22 | + |
| 23 | +Array Cache Adapter |
| 24 | +~~~~~~~~~~~~~~~~~~~ |
| 25 | + |
| 26 | +This adapter is only useful for testing purposes because contents are stored in |
| 27 | +memory and not persisted in any way. Besides, some features explained later are |
| 28 | +not available, such as the deferred saves:: |
| 29 | + |
| 30 | + use Symfony\Component\Cache\Adapter\ArrayAdapter; |
| 31 | + |
| 32 | + $cache = new ArrayAdapter( |
| 33 | + // in seconds; applied to cache items that don't define their own lifetime |
| 34 | + // 0 means to store the cache items indefinitely (i.e. until the current PHP process finishes) |
| 35 | + $defaultLifetime = 0, |
| 36 | + // if ``true``, the values saved in the cache are serialized before storing them |
| 37 | + $storeSerialized = true |
| 38 | + ); |
| 39 | + |
| 40 | +Filesystem Cache Adapter |
| 41 | +~~~~~~~~~~~~~~~~~~~~~~~~ |
| 42 | + |
| 43 | +This adapter is useful when you want to improve the application performance but |
| 44 | +can't install tools like APC or Redis in the server. This adapter stores the |
| 45 | +contents as regular files in a set of directories on the local file system:: |
| 46 | + |
| 47 | + use Symfony\Component\Cache\Adapter\FilesystemAdapter; |
| 48 | + |
| 49 | + $cache = new FilesystemAdapter( |
| 50 | + // the subdirectory of the main cache directory where cache items are stored |
| 51 | + $namespace = '', |
| 52 | + // in seconds; applied to cache items that don't define their own lifetime |
| 53 | + // 0 means to store the cache items indefinitely (i.e. until the files are deleted) |
| 54 | + $defaultLifetime = 0, |
| 55 | + // the main cache directory (the application needs read-write permissions on it) |
| 56 | + // if none is specified, a directory is created inside the system temporary directory |
| 57 | + $directory = null |
| 58 | + ); |
| 59 | + |
| 60 | +APCu Cache Adapter |
| 61 | +~~~~~~~~~~~~~~~~~~ |
| 62 | + |
| 63 | +This adapter can increase the application performance very significantly, |
| 64 | +because contents are cached in the shared memory of your server, which is much |
| 65 | +faster than the file system. It requires to have installed and enabled the PHP |
| 66 | +APCu extension. It's not recommended to use it when performing lots of write and |
| 67 | +delete operations because it produces fragmentation in the APCu memory that can |
| 68 | +degrade performance significantly:: |
| 69 | + |
| 70 | + use Symfony\Component\Cache\Adapter\ApcuAdapter; |
| 71 | + |
| 72 | + $cache = new ApcuAdapter( |
| 73 | + // the string prefixed to the keys of the items stored in this cache |
| 74 | + $namespace = '', |
| 75 | + // in seconds; applied to cache items that don't define their own lifetime |
| 76 | + // 0 means to store the cache items indefinitely (i.e. until the APC memory is deleted) |
| 77 | + $defaultLifetime = 0, |
| 78 | + // if present, this string is added to the namespace to simplify the |
| 79 | + // invalidation of the entire cache (e.g. when deploying the application) |
| 80 | + $version = null |
| 81 | + ); |
| 82 | + |
| 83 | +Redis Cache Adapter |
| 84 | +~~~~~~~~~~~~~~~~~~~ |
| 85 | + |
| 86 | +This adapter stores the contents in the memory of the server. Unlike the APCu |
| 87 | +adapter, it's not limited to the shared memory of the current server, so you can |
| 88 | +store contents in a cluster of servers if needed. |
| 89 | + |
| 90 | +It requires to have installed Redis and have created a connection that implements |
| 91 | +the ``\Redis``, ``\RedisArray``, ``\RedisCluster`` or ``\Predis`` classes:: |
| 92 | + |
| 93 | + use Symfony\Component\Cache\Adapter\RedisAdapter; |
| 94 | + |
| 95 | + $cache = new RedisAdapter( |
| 96 | + // the object that stores a valid connection to your Redis system |
| 97 | + \Redis $redisConnection, |
| 98 | + // the string prefixed to the keys of the items stored in this cache |
| 99 | + $namespace = '', |
| 100 | + // in seconds; applied to cache items that don't define their own lifetime |
| 101 | + // 0 means to store the cache items indefinitely (i.e. until the Redis memory is deleted) |
| 102 | + $defaultLifetime = 0 |
| 103 | + ); |
| 104 | + |
| 105 | +Chain Cache Adapter |
| 106 | +~~~~~~~~~~~~~~~~~~~ |
| 107 | + |
| 108 | +This adapter allows to combine any number of the previous adapters. Cache items |
| 109 | +are fetched from the first adapter which contains them. Besides, cache items are |
| 110 | +saved in all the given adapters, so this is a simple way of creating a cache |
| 111 | +replication:: |
| 112 | + |
| 113 | + use Symfony\Component\Cache\Adapter\ApcuAdapter; |
| 114 | + use Symfony\Component\Cache\Adapter\ChainAdapter; |
| 115 | + use Symfony\Component\Cache\Adapter\FilesystemAdapter; |
| 116 | + |
| 117 | + $apcCache = new ApcuAdapter(); |
| 118 | + $fileCache = new FilesystemAdapter(); |
| 119 | + |
| 120 | + $cache = new ChainAdapter(array($apcCache, $fileCache)); |
| 121 | + |
| 122 | +When an item is not found in the first adapters but is found in the next ones, |
| 123 | +the ``ChainAdapter`` ensures that the fetched item is saved in all the adapters |
| 124 | +where it was missing. Since it's not possible to know the expiry date and time |
| 125 | +of a cache item, the second optional argument of ``ChainAdapter`` is the default |
| 126 | +lifetime applied to those cache items (by default it's ``0``). |
| 127 | + |
| 128 | +Proxy Cache Adapter |
| 129 | +~~~~~~~~~~~~~~~~~~~ |
| 130 | + |
| 131 | +This adapter is useful to integrate in your application cache pools not created |
| 132 | +with the Symfony Cache component. As long as those cache pools implement the |
| 133 | +``CacheItemPoolInterface`` interface, this adapter allows you to get items from |
| 134 | +that external cache and save them in the Symfony cache of your application:: |
| 135 | + |
| 136 | + use Symfony\Component\Cache\Adapter\ProxyAdapter; |
| 137 | + |
| 138 | + // ... create $nonSymfonyCache somehow |
| 139 | + $cache = new ProxyAdapter($nonSymfonyCache); |
| 140 | + |
| 141 | +The adapter accepts two additional optional arguments: the namespace (``''`` by |
| 142 | +default) and the default lifetime (``0`` by default). |
| 143 | + |
| 144 | +Another use case for this adapter is to get statistics and metrics about the |
| 145 | +cache hits (``getHits()``) and misses (``getMisses()``). |
| 146 | + |
| 147 | +Doctrine Cache Adapter |
| 148 | +~~~~~~~~~~~~~~~~~~~~~~ |
| 149 | + |
| 150 | +This adapter wraps any `Doctrine Cache`_ provider so you can use them in your |
| 151 | +application as if they were Symfony Cache adapters:: |
| 152 | + |
| 153 | + use Doctrine\Common\Cache\SQLite3Cache; |
| 154 | + use Symfony\Component\Cache\Adapter\DoctrineAdapter; |
| 155 | + |
| 156 | + $doctrineCache = new SQLite3(__DIR__.'/cache/data.sqlite'); |
| 157 | + $symfonyCache = new DoctrineAdapter($doctrineCache); |
| 158 | + |
| 159 | +This adapter also defines two optional arguments called ``namespace`` (default: |
| 160 | +``''``) and ``defaultLifetime`` (default: ``0``) and adapts them to make them |
| 161 | +work in the underlying Doctrine cache. |
| 162 | + |
| 163 | +Looking for Cache Items |
| 164 | +----------------------- |
| 165 | + |
| 166 | +Cache Pools define three methods to look for cache items. The most common method |
| 167 | +is ``getItem($key)``, which returns the cache item identified by the given key:: |
| 168 | + |
| 169 | + use Symfony\Component\Cache\Adapter\FilesystemAdapter; |
| 170 | + |
| 171 | + $cache = new FilesystemAdapter('app.cache') |
| 172 | + $latestNews = $cache->getItem('latest_news'); |
| 173 | + |
| 174 | +If no item is defined for the given key, the method doesn't return a ``null`` |
| 175 | +value but an empty object which implements the :class:`Symfony\\Component\\Cache\\CacheItem` |
| 176 | +class. |
| 177 | + |
| 178 | +If you need to fetch several cache items simultaneously, use instead the |
| 179 | +``getItems(array($key1, $key2, ...))`` method:: |
| 180 | + |
| 181 | + // ... |
| 182 | + $stocks = $cache->getItems(array('AAPL', 'FB', 'GOOGL', 'MSFT')); |
| 183 | + |
| 184 | +Again, if any of the keys doesn't represent a valid cache item, you won't get |
| 185 | +a ``null`` value but an empty ``CacheItem`` object. |
| 186 | + |
| 187 | +The last method related to fetching cache items is ``hasItem($key)``, which |
| 188 | +returns ``true`` if there is a cache item identified by the given key:: |
| 189 | + |
| 190 | + // ... |
| 191 | + $hasBadges = $cache->hasItem('user_'.$userId.'_badges'); |
| 192 | + |
| 193 | +Saving Cache Items |
| 194 | +------------------ |
| 195 | + |
| 196 | +The most common method to save cache items is |
| 197 | +:method:`Psr\\Cache\\CacheItemPoolInterface::save`, which stores the |
| 198 | +item in the cache immediately (it returns ``true`` if the item was saved or |
| 199 | +``false`` if some error occurred):: |
| 200 | + |
| 201 | + // ... |
| 202 | + $userFriends = $cache->get('user_'.$userId.'_friends'); |
| 203 | + $userFriends->set($user->getFriends()); |
| 204 | + $isSaved = $cache->save($userFriends); |
| 205 | + |
| 206 | +Sometimes you may prefer to not save the objects immediately in order to |
| 207 | +increase the application performance. In those cases, use the |
| 208 | +:method:`Psr\\Cache\\CacheItemPoolInterface::saveDeferred` method to mark cache |
| 209 | +items as "ready to be persisted" and then call to |
| 210 | +:method:`Psr\\Cache\\CacheItemPoolInterface::commit` method when you are ready |
| 211 | +to persist them all:: |
| 212 | + |
| 213 | + // ... |
| 214 | + $isQueued = $cache->saveDeferred($userFriends); |
| 215 | + // ... |
| 216 | + $isQueued = $cache->saveDeferred($userPreferences); |
| 217 | + // ... |
| 218 | + $isQueued = $cache->saveDeferred($userRecentProducts); |
| 219 | + // ... |
| 220 | + $isSaved = $cache->commit(); |
| 221 | + |
| 222 | +The ``saveDeferred()`` method returns ``true`` when the cache item has been |
| 223 | +successfully added to the "persist queue" and ``false`` otherwise. The ``commit()`` |
| 224 | +method returns ``true`` when all the pending items are successfully saved or |
| 225 | +``false`` otherwise. |
| 226 | + |
| 227 | +Removing Cache Items |
| 228 | +-------------------- |
| 229 | + |
| 230 | +Cache Pools include methods to delete a cache item, some of them or all of them. |
| 231 | +The most common is :method:`Psr\\Cache\\CacheItemPoolInterface::deleteItem`, |
| 232 | +which deletes the cache item identified by the given key (it returns ``true`` |
| 233 | +when the item is successfully deleted or doesn't exist and ``false`` otherwise):: |
| 234 | + |
| 235 | + // ... |
| 236 | + $isDeleted = $cache->deleteItem('user_'.$userId); |
| 237 | + |
| 238 | +Use the :method:`Psr\\Cache\\CacheItemPoolInterface::deleteItems` method to |
| 239 | +delete several cache items simultaneously (it returns ``true`` only if all the |
| 240 | +items have been deleted, even when any or some of them don't exist):: |
| 241 | + |
| 242 | + // ... |
| 243 | + $areDeleted = $cache->deleteItems(array('category1', 'category2')); |
| 244 | + |
| 245 | +Finally, to remove all the cache items stored in the pool, use the |
| 246 | +:method:`Psr\\Cache\\CacheItemPoolInterface::clear` method (which returns ``true`` |
| 247 | +when all items are successfully deleted):: |
| 248 | + |
| 249 | + // ... |
| 250 | + $cacheIsEmpty = $cache->clear(); |
| 251 | + |
| 252 | +.. _`Doctrine Cache`: https://github.com/doctrine/cache |
0 commit comments