On a Drupal 6 site I'm profiling, the theme registry takes up to 3.5mb of memory on each request.
An extreme version of what can happen is this lightbox2 issue- where dynamic theme functions are leading to max_allowed_packet being exceeded - and because this cache is requested on every request, that means a full registry rebuild and attempted cache_set() every time. memcache also has a 1mb gzipped limit for cache objects and similar problems have been reported in .
So this patch adds a new function theme_get_hook(), which maintains a static and persistent cache of theme registry entries by hook name, and falls back to the global theme registry cache when a new one is found.
On a default Drupal 7 install with the standard profile, the theme registry takes up 350kb of memory. With this patch, it's 65kb on the first request to the front page. After posting a node, viewing a node, viewing a user profile then visiting the front page again, it was 144kb - still half. I'd imagine the savings to be a lot bigger once you have several contrib modules installed - since rarely is every single part of every single hook_theme() going to be used across a site.
This doesn't actually fix the problem when the theme registry cache gets too big to actually cache (although it would remove the worst of the performance implications since we wouldn't be trying to load the full registry every request), but that's a different problem and harder to solve.
The main drawback here is there will be a number of cache_set() while the smaller cache is being built. The 145kb cache entry I built has 65 entries. However these aren't rebuilds, just requesting the already cached full registry and adding parts of it to the runtime cache.
Did some click around testing while profiling but haven't run simpletests on this. Once this passes I'll do a D6 backport and see how much impact it has on that 3.5mb cache entry.
|PASSED: [[SimpleTest]]: [MySQL] 36,853 pass(es).|
|PASSED: [[SimpleTest]]: [MySQL] 36,468 pass(es).|
|FAILED: [[SimpleTest]]: [MySQL] Failed to run tests: failed to enable simpletest module.|
|PASSED: [[SimpleTest]]: [MySQL] 33,269 pass(es).|
|FAILED: [[SimpleTest]]: [MySQL] Unable to apply patch theme_registry_12_0.patch. This may be a -p0 (old style) patch, which is no longer supported by the testbots.|