Foreword
In our time, a huge number of high-loaded projects topic caching something that was not as relevant as ever. Cached as requests from the database, the individual blocks of the page, and all pages entirely.
For myself, I decided to cache only the results of queries to the database, because, IMHO, to load the cache with huge (or not so) html blocks - in some way wasting resources. (This statement is most likely true only if you are not using the template engine). And of course, as a caching service, I use the well-known memcached.
Now let's see - what problems await us with this caching.
And the problem is only one, but not the most biased - keeping the cache always up to date.
Under the cut - my solution to the problem, allowing the cache to live forever (unless of course it is relevant and you have not run out of RAM).
')
Read more
Adhering to the current MVC model, all requests to the database will be carried out in models. In my projects for each section of the site I have my own separate model, as well as a general model, the data from which are needed in each section.
The key of the cache entry thus consists of the name of the section, the name of the function and the parameters passed to this function. All this turns into md5 in order to prevent too long drains or the transfer of an array of parameters as part of the cache key.
Now, when updating information in the database in 90% of cases, we will definitely know the cache of what functions we need to reset. But this is not always the case. For example, the user deleted the last 5 messages from his personal account, but since all messages are broken, say 10 per page, resetting only the last page cache, all other pages remain cached in the old state, and this is no longer good. The task is to reset the function cache, knowing only 1 of its parameter (user id), but not knowing the second (page number).
So my solution
In short, each time a new entry is added to the cache, the key components are written to Mongo, thereby giving the opportunity to completely recreate the cache key, knowing only a part of it. I will not go into details, just run through the code.
class Cache extends Memcached { private $registry; public function __construct() { parent::__construct(); $this->addServer('localhost', 11211); $m = new Mongo(); $this->registry = $m->local->cache_registry;
And an example of a call, so that everything finally falls into place:
$cache = new Cache(); $cache->smart_delete('user', 'messages', array(1));
As you can see, all the indecency is simple and quite a lot of profit
- Delete all entries from a specific section
- Delete all entries in the section by function name only
- Delete all function entries, knowing only the required parameter and discarding unnecessary ones.
Of course, despite the fact that it is implemented now it is impossible to delete a record, knowing only the second parameter and not knowing the first one, which obliges you to think through the order of parameters at the moment of creating the function. Or delete records of the same functions from different sections (why not?), But I think that if there is free time, all this is completely realizable.
PS All with the last holidays!