4

A portion of my template is being cached, using the standard cache tag:

{% cache %}

Within that cached section of the template, I'm using a template hook:

{% hook 'myTemplateHook' %}

Within that template hook, I'm collecting entry data via a normal ElementCriteriaModel:

$criteria = craft()->elements->getCriteria(ElementType::Entry);
$criteria->section = 'mySection';
$myEntries = $criteria->find();

So I'm wondering... Will my PHP-based query be cached?

I'd like for the caching of this query to mimic any caching that would take place via Twig templates. What do I need to do to ensure this follows normal caching patterns?

EDIT:

Great answers so far, but they don't really touch on the heart of my concern...

Normal Twig-based caches actually record all criteria and elements used in the cached HTML, for the purpose of invalidating that cache when either of those things change. What I really want to know is, would my PHP-based criteria and resulting elements be recorded as well? Since the criteria is built in PHP, and the elements are collected in PHP, I'd like to know if they are being stored (as they normally would via Twig).

This obviously makes a difference for cache invalidation... If an element fetched via PHP is updated or deleted, I'd like to be confident that the cache would be cleared as well.

3

Yes, sort of. As soon as the rendering template hits a {% cache %} tag, Craft grabs the outputted content from the cache table in the database and ignores all other template logic until the {% endcache %} tag.

So, the results of the PHP-based query will be cached with the rest of whatever is between the tags only for use in that instance as HTML.

If your hook is called anywhere else, Craft will make the PHP query again, as the query itself is not cached independently. In order to accomplish that (if you want), you will need to implement some plugin-level cacheing using the Cache Service.

For cache invalidation, here is what Brandon has to say:

Any time ElementCriteriaModel::find() et al. is called within {% cache %} tags, it will be recorded, however you will have to manually register any elements that should be associated with the cache, using this code:

// Don't initialize the CacheService if we don't have to
$cacheService = craft()->getComponent('templateCache', false);

if ($cacheService)
{
    $cacheService->includeElementInTemplateCaches($elementId);
}
  • Great, thanks Aaron... That info on cache invalidation was exactly what I was looking for! – Lindsey D Jun 23 '15 at 17:08
2

My understanding is that the {% cache %} tag operates like a conditional. If it succeeds (cache hit), then output the cached value. If it fails (cache miss), then calculate the value (run everything between the {% cache %} and {% endcache %} tags), cache it for later, and output it.

So I don't think you need to do anything special. Your hook will be run (and the result cached) only when the code inside the {% cache %} tag is run, which is whenever there is a cache miss.

  • Thanks Marion, great answer! But I'm gonna give this one to Aaron, since he touched upon cache invalidation as well. – Lindsey D Jun 23 '15 at 17:09
  • I would have given it to Aaron too – Marion Newlevant Jun 23 '15 at 17:12
  • Lol! I still very much appreciate the answer. :) – Lindsey D Jun 23 '15 at 17:13
0

More than you ever wanted to know about the Craft {% cache %} tag:

The Craft {% cache %} Tag In-Depth

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.