_block_rehash() is a function that loops through all code-declared blocks for a given theme and writes/updates their database entries. It's called by block_flush_caches(), which is invoked on all cron runs when system_cron() attempts to get a list of cache bins to flush. Even if cache_clear_all determines that the block cache doesn't need to be flushed (due to cache minimum lifetime), because _block_rehash() is called directly in the Block module's hook_flush_caches() implementation, it's run on every cron run. That means that there's a DB insert or update for every block declared in code for every active theme on every cron run.
If you happen to have a lot of blocks declared in code, or even a relatively small number of blocks declared in code, but have several active themes, your cron run may take ages to complete, or run out of memory and fail completely, etc. This problem may be especially aggravated if you use the Nodeblock module. This is especially a problem if you run cron often.
There may be a few ways to cut down on the number of times _block_rehash() gets run.
- Rather than running _block_rehash() in block_flush_caches() (which seems like a hack), we could probably move it to block's own implementation of hook_cron(). In D8, we could make how often it gets run configurable (though maybe not necessary); in D7, we could make it a hidden variable that defaults to the minimum cache lifetime.
- Another way would be to wrap the call to _block_rehash() in block_flush_caches() with some logic that respects minimum cache lifetime (by either piggybacking off of cache_flush_cache_block or adding a new, similar variable that respects minimum cache lifetime). This might not make the most sense, since this isn't technically cache-related.
- Just makes sure the database does not get updated all the time. There are only three things that can happen to a block coming from the database: the cache gets changed, it goes from enabled to disabled due to invalid region and alter does something. We can track the first two, the third we can compare.
Discuss which of the above resolutions is most appropriate, then implement.
User interface changes
Depends on discussion, but probably none.
If anything, this would be an API addition, but there are ways we could avoid any API changes. See proposed resolutions above.
PASSED: [[SimpleTest]]: [MySQL] 40,629 pass(es).
[ View ]
PASSED: [[SimpleTest]]: [MySQL] 40,642 pass(es).
[ View ]