Problem/Motivation
See parent issue's issue summary.
Proposed resolution
Automatically set #create_placeholder (added by #2478483: Introduce placeholders (#lazy_builder) to replace #post_render_cache) whenever max-age = 0 is bubbled up.
This will be based on Fabianx' prototype/PoC work over at #2478483-8: Introduce placeholders (#lazy_builder) to replace #post_render_cache and #2469431-31: BigPipe for auth users: first send+render the cheap parts of the page, then the expensive parts.
Remaining tasks
- Required base API:
First get #2478483: Introduce placeholders (#lazy_builder) to replace #post_render_cache in. Auto-placeholdering for#lazy_builderwithout bubbling: #2543332: Auto-placeholdering for #lazy_builder without bubbling- Auto-placeholdering for
#lazy_builderwith bubbled cache contexts and cache tags: #2543334: Auto-placeholdering for #lazy_builder with bubbling of contexts and tags- Auto-placeholdering for
#lazy_builderwith bubbled max-age: #2559847: Auto-placeholdering for #lazy_builder with bubbling of max-age. - Auto-placeholdering without
#lazy_builder: #2543336: Auto-placeholdering without #lazy_builder
- Auto-placeholdering for
- Auto-placeholdering for
- Conversions:
#2543554: Clean up Help & Statistics blocks- Convert
BlockViewBuilderto use#lazy_builder: #2543340: Convert BlockViewBuilder to use #lazy_builder (but don't yet let context-aware blocks be placeholdered)
User interface changes
None.
API changes
TBD, but likely none.
Comments
Comment #1
wim leers#2478483: Introduce placeholders (#lazy_builder) to replace #post_render_cache landed, so this is now unblocked!
Comment #2
wim leersClarifying tasks and why they're not API changes.
Comment #3
fabianx commentedIn the best case here or in follow-ups we do:
- #2469431-31: BigPipe for auth users: first send+render the cheap parts of the page, then the expensive parts (comment 31)
I outlined the 4 cases there that need to be supported for auto-placeholdering to be the most effective and especially not needing to rely on lazy builders, when the information is cacheable.
Comment #4
wim leersAttribution & process
I've drawn from Fabianx' prototype/PoC work over at #2478483-8: Introduce placeholders (#lazy_builder) to replace #post_render_cache and #2469431-31: BigPipe for auth users: first send+render the cheap parts of the page, then the expensive parts. But, only for general/initial guidance: I've gone my own way, for two reasons:
In the past two weeks, I've spent many, many hours on this. Since it is crucial for both #2429617: Make D8 2x as fast: Dynamic Page Cache: context-dependent page caching (for *all* users!) and #2469431: BigPipe for auth users: first send+render the cheap parts of the page, then the expensive parts, both of which are able to deliver massive speed-ups. This issue (auto-placeholdering), just like those two (SmartCache & BigPipe) heavily exploit cacheability metadata.
(I just want to mention again that I now believe even more that a tool like http://wimleers.com/blog/renderviz-prototype will both be A) crucial for efficient Drupal 8 development, B) put Drupal 8 miles ahead of other frameworks. I think/hope I'll be able to work on that as the next big thing after SmartCache/BigPipe.)
Overview & recap
Now, let's get down to business. Auto-placeholdering is conceptually trivial: any render array that has a
#lazy_builder(meaning it can be built in isolation) and that has poor cacheability (max-age=0or such asuserorsession), is turned into a placeholder. As a (intended) consequence, this means that poor cacheability is cordoned off: it does not "poison" its containing elements (its parents), and therefore does not poison the rest of the page/response. Which then means that SmartCache can effectively cache the skeleton (the entire HTML response minus the parts that are placeholdered) of … pretty much every HTML response in Drupal! That then also has as a consequence that BigPipe will be able to just get entire skeletons directly from SmartCache, then just needing to render the placeholders and stream them to the user. In other words: this issue is crucial for both SmartCache & BigPipe.But … some parts of it implementation are not at all trivial, because to have auto-placeholdering work for every use case, we need it to also work for both bubbled high-cardinality cache contexts (#2429257: Bubble cache contexts) and bubbled max-age=0. This means that we need to make the
RenderCacheservice smarter: if a render cached element is noticed to have poor cacheability, and it is for an element with a#lazy_builder, then it can choose to return a placeholder instead of the render cached element. Which means that the system automatically learns which parts of the page are uncacheable.Finally, it is actually technically possible to remove the
#lazy_builderrequirement. Which means all of the above applies to anything that is render cacheable. But, there are some caveats here: race conditions (what if the render cache item is invalidated after we already determined it is available and therefore safe to placeholder?) that can only be resolved with fairly complex solutions (if the render cache item disappeared, we'll have to re-execute the original request to regenerate the render cache item — yes that's scary). So we'll leave that for a follow-up. For now, the above should suffice.Results
I've split it up into four issues.
#lazy_builderwithout bubbling: #2543332: Auto-placeholdering for #lazy_builder without bubbling#lazy_builderwith bubbled cache contexts (and max-age=0, though we may want to split that part off): #2543334: Auto-placeholdering for #lazy_builder with bubbling of contexts and tags#lazy_builder: #2543336: Auto-placeholdering without #lazy_builderBlockViewBuilderto use#lazy_builder: #2543340: Convert BlockViewBuilder to use #lazy_builder (but don't yet let context-aware blocks be placeholdered)Issues 1 (without bubbling) and 2 (blocks) can be done in parallel. Issue 1.1 (with bubbling) is blocked on 1, and 1.1.1 is blocked on 1.1. Issue 1.1.1 can be postponed to 8.1.
Comment #5
wim leersComment #6
wim leers#2543332: Auto-placeholdering for #lazy_builder without bubbling and #2543340: Convert BlockViewBuilder to use #lazy_builder (but don't yet let context-aware blocks be placeholdered) — which can happen in parallel — now both have green patches.
In doing the latter, we also discovered the need for #2543554: Clean up Help & Statistics blocks, which also has a green patch.
Patch for #2543334: Auto-placeholdering for #lazy_builder with bubbling of contexts and tags is coming up next, have it working locally already.
Comment #7
wim leers#2543332: Auto-placeholdering for #lazy_builder without bubbling just landed!
Comment #8
wim leers#2543554: Clean up Help & Statistics blocks also landed.
IS updated to more clearly show remaining tasks.
Comment #9
wim leersComment #10
wim leers#2543340: Convert BlockViewBuilder to use #lazy_builder (but don't yet let context-aware blocks be placeholdered) and #2543334: Auto-placeholdering for #lazy_builder with bubbling of contexts and tags are now blocked on review. Both have green patches and have already gotten some reviews. We just need to push them to the finish line.
If the first lands, we'll already have basic auto-placeholdering of blocks in D8 core, which will be sufficient for SmartCache to land: #2429617: Make D8 2x as fast: Dynamic Page Cache: context-dependent page caching (for *all* users!) :)
Comment #11
wim leersSplit off the portion of #2543334: Auto-placeholdering for #lazy_builder with bubbling of contexts and tags that handled bubbled max-age to a separate issue: #2559847: Auto-placeholdering for #lazy_builder with bubbling of max-age — like originally predicted when I wrote this issue summary :)
Comment #12
wim leersOh, and #2543340: Convert BlockViewBuilder to use #lazy_builder (but don't yet let context-aware blocks be placeholdered) just landed :)
Comment #13
joelpittet