Follow-up from #1982024: Lazy-load Attribute objects later in the rendering process only if needed.
Problem/Motivation
We have 3 special attribute variables in preprocess: 'attributes', 'title_attributes', and 'content_attributes'
.
When built in preprocess they are created as arrays while all other $variables keys for attributes need to be instantiated as new Attribute(...)
This presents a DX issue where you need to know something about the internals to understand how it works.
There are two things that this does 'for' us that I'm aware:
- It makes those un-Attribute()'ed variables easier to merge as arrays (RDF module I believe does this)
- Provides a 5.652ms performance gain #1982024-7: Lazy-load Attribute objects later in the rendering process only if needed for wall time. Which could be solved with this #2048637: Add #type => 'attributes' and wrap in Attribute class with drupal_pre_render_attributes
With lazy loading certain $variables keys ('attributes', 'content_attributes', 'title_attributes')
//
function template_preprocess_something(&$variables) {
// Special variable keys.
$variables['attributes'] = array('class' => array('i', 'am', 'lazy', 'and', 'special'));
$variables['title_attributes'] = array('class' => array('me', 'two'));
$variables['content_attributes'] = array('title' => "Don't forget me too");
// The rest of the gang.
$variables['nested']['attributes'] = new Attribute(array('src' => '/not/special/either.gif'));
$variables['whatever_attributes'] = new Attribute(array('alt' => 'Un fair:-(');
}
Without lazy loading
function template_preprocess_something(&$variables) {
// Playing fair and consistant.
$variables['attributes'] = new Attribute(array('class' => array('i', 'am', 'a', 'work', 'horse')));
$variables['title_attributes'] = new Attribute(array('class' => array('me', 'two')));
$variables['content_attributes'] = new Attribute(array('title' => "not as fast but fair is fair."));
// The rest of the gang.
$variables['nested']['attributes'] = new Attribute(array('src' => '/img/same.gif'));
$variables['whatever_attributes'] = new Attribute(array('alt' => 'just like funky and the bunch');
}
Proposed resolution
Remove this chunk of code from the bloated theme() function
if (!isset($default_attributes)) {
$default_attributes = new Attribute();
}
foreach (array('attributes', 'title_attributes', 'content_attributes') as $key) {
if (isset($variables[$key]) && !($variables[$key] instanceof Attribute)) {
if ($variables[$key]) {
$variables[$key] = new Attribute($variables[$key]);
}
else {
// Create empty attributes.
$variables[$key] = clone $default_attributes;
}
}
}
And instantiate those attributes when they are needed/used in the templates and not before.
Update
Removing all 3 was challenging in one patch. This patch is now dedicated to only remove title_attributes
and content_attributes
. A follow-up will be opened to deal with the attributes
key after this one is committed.
Remaining tasks
Discuss any other drawbacks to removing this.Create a patch- Create follow-up issue to finish the job with $variables['attributes']
User interface changes
N/A
API changes
N/A
Related Issues
Comment | File | Size | Author |
---|---|---|---|
#126 | interdiff.txt | 1.17 KB | joelpittet |
#126 | remove_special_cased-2108771-126.patch | 8.45 KB | joelpittet |
#124 | interdiff.txt | 4.93 KB | joelpittet |
#124 | remove_special_cased-2108771-124.patch | 9.49 KB | joelpittet |
#123 | interdiff.txt | 1.73 KB | joelpittet |
Comments
Comment #1
joelpittet.
Comment #2
webchickComing in as a layperson to all of this, the proposed "explicitly load whenever needed consistently" way definitely makes more logical sense to me. But I'd love to hear from FabianX and steveoliver and anyone else involved at the original issue.
Comment #2.0
webchickUpdated issue summary.
Comment #3
Fabianx CreditAttribution: Fabianx commentedI don't think it is a good idea, to do it.
In my book, I even would propose to #type those Attribute arrays.
The early instantiation is very unnecessary and the performance is one magic call per array access.
Again the problem is less the magic access, but that people "think" it is fast to use, which is much larger DX problem.
I think removing __set from it could work and making them read-only; instantiate once in the end.
Attribute objects are only useful at the presentation layer for output so that you can print the class first and the rest later.
Again, I think the real DX win is if we have "lightly" typed data in our theme layer that defines that these variables are "attributes".
Because in the end you will need to know in a template if something is an attribute or not, so it needs to happen in a late preprocess / prepare step anyway to convert to new Attribute().
And those magic classes are nothing new, they existed as the much more confusing and less consistent classes_array already in D7 ...
---
EDIT:
Also the current code perfectly works when instantiating the Attribute() objects early. So this could be thought of as an internal optimization as well and we will likely need more internal optimizations rather than less.
Comment #4
Fabianx CreditAttribution: Fabianx commentedThis is related to performance ...
Comment #5
joelpittet@Fabianx, having a #type'd array for attributes would be more consistent and very likely faster.
My main concern is like you hinted in the "EDIT". Though my counter argument there is that even though it is an 'internal optimization' people are looking to the preprocess layer and templates as a way to get hints on how to do things in their themes. This provides unnecessary confusion as it is now with 3 key'd variables getting treated differently than the rest. So it is front facing.
#type=>attributes is an issue #2048637: Add #type => 'attributes' and wrap in Attribute class with drupal_pre_render_attributes and at first I was confused about what that was, then after you explained it so well in #3 it makes more sense. Personally I'd still like to be able to manipulate the Attribute object at twig time but using the following would make it easier to merge and manipulate and possibly be a better DX win.
FYI this issue would still be relevant in removing those magic keys:)
Comment #5.0
joelpittetUpdated issue summary.
Comment #6
joelpittetChanging the title on this because it's not the lazy-loading I want to remove, it's the special keys.
Comment #6.0
joelpittetUpdated issue summary.
Comment #7
jenlamptonMost templates don't need all three of these variables, so I'd love to remove them :)
Another thing to note here is that these keys are also incorrectly named. By the time we get to the template we should be printing
{{ title.attributes }}
and{{ content.attributes }}
not title_attributes and content_attributes. That means these attributes should really be attached to the thing they are describing (title and/or content) and not free-floating. To make things make sense, what we need is correctly structured data.Removing these here means we can add attributes where they are actually needed: in the correct places - and with the correct names.
Comment #8
joelpittetI very highly doubt this will pass all the tests... but here's a rough to see how much effort this issue will be.
Comment #10
webchickThat's an impressive number of exceptions, sir! :)
Comment #11
joelpittetI could do more, look how many tests are run, room for 'improvement'
Comment #12
star-szrJust reverting #1982024: Lazy-load Attribute objects later in the rendering process only if needed is too much of a DX (difficult to manipulate or merge in attributes later in the preprocess/prepare stack) and performance regression IMO.
In general I would love to remove the special casing we have though, and #2048637: Add #type => 'attributes' and wrap in Attribute class with drupal_pre_render_attributes seems like a viable way forward at first glance.
Comment #13
joelpittetYeah that one has some nice
917 fail(s), and 1,588 exceptions.
And less code to fail that little:) The #type => attributes will work but only if we find a way to either convert early without the recusive $variables search, OR convert late but replace the array with a TwigReference on the fly when key's are accessed in {{ twig.attributes.key }} get's printed.
Comment #14
c4rl CreditAttribution: c4rl commentedFirst of all, let's clarify that the *relative* performance gain in #1982024-7: Lazy-load Attribute objects later in the rendering process only if needed was less than 1%.
IMHO, the motivating factor of #1982024: Lazy-load Attribute objects later in the rendering process only if needed is an anti-pattern: Attribute() objects should be instantiated as such from the start, period. If they aren't used, is that such a problem? Are we really that afraid of instantiating objects? By having this fear, we create other problems.
We are only obscuring the fact that Attribute() objects are special things by putting them in some sort of '#type', which works now completely differently than other things that have '#type.'
For the sake of true consistency: I would much prefer to have Attribute objects always be Attribute objects and not arrays that are later converted.
Comment #14.0
c4rl CreditAttribution: c4rl commentedUpdated issue summary.
Comment #15
joelpittetA re-roll and add the prepped empty arrays back in. Should have less exceptions.
Comment #17
joelpittetJust want to say +1 for #14 Thanks c4rl that is my sentiment exactly. Also, the only reason this Attribute class really *needs* to exist is for the handy little #printed magic it does for
<tag class="{{ attributes.class }}"{{ attributes }}>
which, if this got in: #2114563: Remove TwigReference with the help of 'without' filter replacing 'show'/'hide' functions. could be replicated with<tag class="{{ attributes.class }}"{{ attributes|hide('class') }}>
...Comment #18
rteijeiro CreditAttribution: rteijeiro commentedComment #19
joelpittetPicking this back up.
Comment #20
joelpittetRe-rolled.
Comment #23
joelpittetremove a few more exceptions and such.
Comment #24
joelpittetComment #27
joelpittetThis will cut down a good chunk of exceptions *crosses fingers* more than half?
Comment #29
joelpittetOk I'm simplifying this because there is too much engrained. This is a compromise patch, removing title_attributes and content_attributes special variables. Also would be nicer to deal with if there wasn't 'render element'...
Comment #31
joelpittet29: 2108771-special-attribute-keys-29.patch queued for re-testing.
Comment #33
joelpittetNot sure the deal there... but undoing the form.inc change.
Comment #35
joelpittet33: 2108771-special-attribute-keys-33.patch queued for re-testing.
Comment #36
joelpittetThis should fix those last 3...
Comment #38
joelpittetRe-roll. This needs review:)
Comment #40
joelpittetWhoops, wrong patch! That has both 'attributes' and the other two. I'm aiming for just the other two...
Comment #42
joelpittetFixed typo
Comment #43
joelpittetThis may be premature optimisation. Thoughts?
Comment #44
joelpittetAdding tag.
Comment #45
star-szrChanging focus tag to sprint, that is the convention other initiatives have been using and is how I had set up http://drupaltwig.org/issues/focus.
Comment #46
joelpittetRe-roll.
Comment #48
joelpittetOk second time I've done that. This is the right patch with only the title_attributes and content_attributes not automagically converted to Attribute objects.
Going to actually get this in my repo so it doesn't happen again...
Comment #49
joelpittetComment #51
joelpittetThis should be easier to fix up than 400K exceptions;)
Comment #52
joelpittetComment #53
star-szrTagging for reroll.
Comment #54
joelpittetRe-rolled.
Comment #55
joelpittetLet's see were this is at.
Again this isn't everything but it's a big step forward to removing the special case and the confusion between what is an array in preprocess and what is an Attribute object. This still leaves $variables['attributes'] as an array, but makes content_attributes and title_attributes act like all the other attributes in the system.
Comment #56
joelpittetSmall little consistency change from @davereid. Going to performance test this.
Comment #57
joelpittetwhoops.
Comment #58
joelpittetre #57 so wow, I didn't expect a ~3% performance gain when when the reason they are like that to start was for performance... maybe I need someone else to double check?
Comment #59
joelpittetSecond set of results just to see not a fluke.
=== 8.x..8.x compared (538a638f2c760..538a642c85962):
ct : 75,451|75,451|0|0.0%
wt : 602,296|614,504|12,208|2.0%
cpu : 594,238|606,226|11,988|2.0%
mu : 45,144,536|45,144,536|0|0.0%
pmu : 45,219,424|45,219,424|0|0.0%
Profiler output
=== 8.x..2108771-remove-special-variables-keys-56 compared (538a638f2c760..538a6499b782f):
ct : 75,451|75,385|-66|-0.1%
wt : 602,296|611,801|9,505|1.6%
cpu : 594,238|603,185|8,947|1.5%
mu : 45,144,536|45,142,960|-1,576|-0.0%
pmu : 45,219,424|45,216,008|-3,416|-0.0%
Profiler output
Comment #60
Dave ReidThis looks good to me, but could maybe use someone more ingrained in the the theme system in D8 to give a final OK.
Comment #61
benjifisherI created a node with three custom blocks and four comments. Before applying the patch, I see this markup in one of my comments:
Looking at comment.html.twig in the Bartik theme, it looks as though the attributes on the h3 element are the title attributes and the class on the outer div is the content attribute.
After applying the patch, I see exactly the same markup:
When profiling, I see (if I am reading this correctly) a performance improvement after applying the patch, although the difference is small enough that it might be random. The important difference is "ct": is that the total number of function calls while building the page, or is it finer than that?
http://www.lionsad.de/xhprof-kit/xhprof/xhprof_html/?run1=53923d861ff11&...
http://www.lionsad.de/xhprof-kit/xhprof/xhprof_html/?run1=53923d861ff11&...
Comment #62
star-szrPatch looks great to me. This will need a small change record before commit, updating the issue summary to indicate this is only affecting title_attributes and content_attributes, not the main 'attributes', would be a great step in the right direction.
Comment #63
joelpittetComment #64
msonnabaum CreditAttribution: msonnabaum commentedJust went over this with joelpittet and I dont think there's a performance difference here worth considering. Certainly not enough to outweigh the DX improvement.
Comment #65
joelpittetRe-rolled.
Comment #67
joelpittetHmm, well that re-roll needed some tweak.
Comment #68
joelpittet50 nodes in the front page view with bartik.
Sidebars added for recent comments and recent content as well as who online block.
Pretty negligible.
http://www.lionsad.de/xhprof-kit/xhprof/xhprof_html/?run1=5394e21e9bd45&...
http://www.lionsad.de/xhprof-kit/xhprof/xhprof_html/?run1=5394e21e9bd45&...
Comment #69
joelpittetComment #70
star-szrSo the issue summary could use an update to explain that this is only changing title_attributes and content_attributes I think.
One more question:
Why does block use NULL and everything else use new Attribute()? I know this one is the only one with a performance comment but then why aren't all the other ones using the same pattern?
Comment #71
joelpittetThanks @Cottser, it should be consistent through-in-through. Thanks for reviewing and noticing. Also the template should expect that this variable is one type of thing, an Attribute object... sometimes. So I'll change this and also retest.
I've added a note about the followup to the Proposed Resolution of the issue summary.
Comment #72
joelpittetHmm sorry I did a combined re-roll and the change in #70 The interdiff is fairly useless because I missed something in the reroll as some aria stuff got dropped and re-added.
Comment #74
joelpittetAh that failed because we can no longer assume content_attributes exists before because the content class was removed.
Comment #75
joelpittetRe-rolled.
Comment #77
joelpittetFix the comment field
Comment #79
joelpittetThose error could be fixed but they would be easier to look at once this is in: #2285451: Create addClass() and removeClass() methods on Attribute object for merging css class names.
Comment #80
benjifisherIt looks as though #2285451: Create addClass() and removeClass() methods on Attribute object for merging css class names. has been committed, so I am moving this back to NW.
Comment #81
joelpittetLet's see how testbot likes this!
Comment #82
Fabianx CreditAttribution: Fabianx commentedCan we please keep the default implementation of using clone for $default_attributes when its empty?
The optimization is still worth it though it could look like
<?php
if (isset($variables['attributes']) && !($variables['attributes'] instanceof Attribute)) {
if ($variables['attributes']) {
$variables['attributes'] = new Attribute($variables['attributes']);
} else {
if (!isset($empty_attributes)) {
$empty_attributes = new Attribute();
}
$variables['attributes'] = clone $empty_attributes;
}
}
And _theme is really much critical render path.
Again, lets please keep this.
clone is way faster than new and the added complexity is not much ...
Can also use if() and create on the fly.
Especially if you add even more new Attribute() calls.
Block is more seldomly called, so okay with not optimizing here.
This is a bad idea, because now content_attributes, etc. is special, while attributes is not.
What if I write:
$vars['attributes']->addClass()
which is a performance nightmare obviously.
Overall nice, but this introduces other special case (ugh) and reduces performance by removing clone's.
Lets not do that ...
EDIT:
On the benchmarks, with many many fields the performance is still seeable for clone vs. new() and it really does not hurt, while I don't care at all about content_attributes or title_attributes.
Comment #83
joelpittet@Fabianx It hasn't seemed to be a "performance nightmare" in my recent profiling on this issue. @see #68
This original issue was to remove all the late wrapping of arrays to Attribute objects. That was a daunting task and I skirted around 'attributes' key because it's everywhere, though the goal is still to make those consistent as well and not sometimes (in preprocess) arrays, and sometimes (in preprocess and templates) Attribute objects.
So it's only a 10K patch, maybe I need to finish the job here instead of splitting it into to jobs. Also pondering if I can some how instantiate the empty attribute object in the hook_theme, but not sure if I can with 'render elements' yet but I'll give that a try too so we aren't defining their type so late in the processes.
And this is loosely related to the banana plan of getting classes out of the preprocess. #2289511: [meta] Results of Drupalcon Austin's Consensus Banana
Comment #84
Fabianx CreditAttribution: Fabianx commentedOkay, removing performance tag. I am officially giving up on that kind of optimizations hereby.
Lets move everything to objects and deal with the issue by adding more and extensive render caching and using PHP-VM, etc.
Performance (in raw page speed generation time) and Drupal 8 just don't match and that is okay, but lets not say we do ...
We have better strategies to deal with that ...
And I am happy about that cause it means we can cleanup some more things to be objects, etc. without worrying about it and concentrate on the really important things like DX and improved caching.
Comment #85
joelpittet@Fabianx I don't mean to offend you if I have, it's hard to read sarcasm in emails/comments though I hope it's not that and this is seriously ok?
I did the performance test with render cache turned off (before that NULL cache bin was broken in head).
I really don't want to introduce a performance bottle neck that's why I took the time to xhprof this change to the best of my ability. I do plan to do another performance after the 'attributes' key is an object as well, though if the test scenario or strategy is useless I don't want to spend X hours setting it up and running for nothing?
Caching is a great way to increase performance by a heap load but it seems to mask the hell out of real bottlenecks in code. So turning cache off (or turning off the right cache for the test) is key(quite sure you taught me that;)
Comment #86
Fabianx CreditAttribution: Fabianx commented#85:
I really appreciate you taking the time to benchmark things, but the rest of core does not and all the convert X to service issues all add up a little and way more.
My little 'use clone instead of new' optimization is useless compared to the performance hit we are taking elsewhere in core.
This issue taught me that now.
And while it is definitely great to benchmark the attributes to class one again before doing the changes, this should not hold it up - as long as the rest of core is not benchmarked in the same way as the DX win is too great for consistency, etc.
A class based structure will always be slower, but if we call node->getField()->getIterator()->getWhatever and other chained things frequently, we can as well call $attributes->addClass().
We just need to stop saying the theme system is different in terms of performance or in the render chain:
No, it is not. If others in core (in every other issue) don't care about performance, I do not either and all I want is equality in that.
The theme system benchmarks only makes it clearer that core gets slower and slower, but that is not due to the theme system itself, but elsewhere.
The render / theme chain is not special and should not be treated special. That is all my frustration with that.
Lets keep up the great benchmarks, but just don't worry about performance for the moment so much and especially not little micro things like clone vs. new, etc. but on clean OO architecture. Yes, its slower, but that battle has long been lost already and with PHP-VM / PHP 6 things will get way faster in the future, so this is like:
assembly vs. OOP - yes assembly is faster, but no you don't wanna write it.
So totally agree with removing all the special casing :).
Thanks for that! Keep up the great DX!
Comment #87
joelpittet@Fabianx thank you, that is very clear! I'll continue to bench(also because I'm curious of notable differences).
The biggest DX issue that addClass() seems to clean up is that ArrayAccess leads people to think that Attribute is an array. And leads to people blindly doing
And without initializing that class key as an array, you get a nasty error of "indirect modification blah blah blah".
Which you wouldn't get with a normal array but since this fixes but clobbers any class property from being passed into the render array it becomes a catch 22:
Which leads to:
So treating Attribute as an object has some nice DX improvements that solve this extra thinking of "Is this an Array or Attribute object? Is the 'class' AttributeArray created?"
Still very curious though if I can instantiate it earlier if the theme/template expects that variable(in hook_theme()). Though 'render element' doesn't provide much of a 'contract' of what the template expects for variables.
Comment #88
star-szrBump, this needs a reroll.
Comment #89
joelpittetRe-roll and added back the cloning $default_attributes for now. Would like to go full tilt on this for attributes but it's a daunting task and would likely break other issues into rerolls. This however, with just title_attributes and content_attributes, is relatively small.
Maybe we can put this in as-is? And work on the big kahuna key 'attributes' after in a follow up?
Comment #90
star-szrSo are we saying addClass/removeClass is the way to go for any non-template_preprocess function modifying classes? What about modifying other attributes, does that work?
Comment #91
joelpittet@Cottser currently we are using ArrayAccess to modify other attributes. Classes because they are stored as an array are a bit tricky and that's why addClass/removeClass works well because it ensures the array exists as I was trying to demo in #87.
I believe there is another issue around for .setAttribute()/.removeAttribute() discussion.
ArrayAccess fails when it's nested array like objects and the first one dictates the second.
Comment #92
Fabianx CreditAttribution: Fabianx commentedWe _could_ have solved that by internally always populating the class key with an empty array on Attribute creation though, because we check for empty class IIRC ...
Would that not be cleaner, then having two ways ArrayAccess or addClass to set things on attribute objects?
Comment #93
star-szrYeah that thought crossed my mind as well :)
Comment #94
joelpittet@Fabianx and @Cottser, I did attempt to do that in one or two issues earlier. Though I didn't think to actually pre instantiate which is an interesting idea though never crossed my mind. I looked at ways to check if the first key coming in is class and special case it (even though there is one or two RDF attributes that use Attribute Array as well).
Though the addClass() merges, which should clean up in preprocess likely or at least help the DeepMerging that happens in come preprocesses. Also we had some instances of duplicate classes, which also doesn't happen anymore, and in the template there is no extra spaces because the method acts on the object and we don't have to use |without to meet our needs. (Reason for that is that internally Twig merge check is_array() and ArrayAccess is not an array and doesn't merge like Arrays, and I want to avoid hacking core, twig core, at all costs).
So I think "solved" needs by instanciating it, may have solved one issue I think addClass() method solved much more. Not to mention it looks like jQuery and for themers that is a plus(I think that was along the lines of your comment in another issue regarding adding addClass, IIRC @Fabianx)
Comment #95
Fabianx CreditAttribution: Fabianx commentedI am okay with it, just wanted to know the reasoning.
Should we add an attr() method, too? To be consistent?
Comment #96
joelpittet@Fabianx I was thinking we should, but naming conventions could be tricky. FYI That discussion is happening here: #2325517: Add methods for adding/removing attributes (not classes) on Attribute objects
Comment #97
joelpittetRe-rolled.
Comment #103
mikispeed CreditAttribution: mikispeed commentedRe-rolled.
Comment #104
lauriiiComment #106
davidhernandezComment #107
jjcarrionI have made the re-roll from the #97 (the #103 didn't apply).
In the patch #97 there was a change in the way to add the class in the search.module.
I have removed that change because otherwise it breaks the whole site. I have left it like this:
$variables['attributes']['class'][] = 'container-inline';
Comment #109
lauriiiFor me lates patch caused forever loop/php timeout
Comment #110
star-szrWhat are we thinking about this one now folks? Disruptive? Not too disruptive?
Comment #111
joelpittetToo cool for school...
Actually if we remove the item_attributes piece that isn't in scope this is fairly small patch.
Comment #112
joelpittetHere's a re-roll without the field_attributes changes.
Things got a bit simpler/more consistant since classy moved classes out of core! Big win there:)
Comment #114
joelpittetWhoops wrong remove-...*.patch.
Comment #116
davidhernandezWe still need the attributes for node, correct? Those disappeared at some point.
Also, there is a fail for Drupal\datetime\Tests\DateTimeFieldTest which makes no sense. I can't actually get this test to pass locally, with or without the patch. I checked previous commits and still can't get it to pass. The date format is correct, but the date is off by one day. Is there some odd environment issue, or something timezone related?
Comment #118
joelpittet@davidhernandez thanks, that knocked back one failure. The date field seems to be getting it's datetime wrapper required classes in some weird way, looking to track it down.
To test it, just create a 'required' date field on the article type and see the field is missing the h4 classes.
Comment #119
davidhernandezFor me, the issue isn't with the markup. I'm getting local failures on the date value itself. It's annoying, but I'll upload what I have to see if testbot at least is happier.
Also, I assume every occurrence should be accounted for then? There are other places where title_attributes and content_attributes appear, like aggregator.
Comment #120
joelpittetNice! I spent a bunch more time last night trying to solve the problem thinking it was more systemic:S
Comment #121
star-szrSounds like more work is needed then based on #119.
Comment #122
davidhernandezLooks like aggregator might have been the only thing left. Everything else looks covered, mostly by the field change.
Comment #123
joelpittetI'd like to do this for all of them... (see interdiff) but it only works for variables and all the rest are 'render element'. Boo to 'render element'!
It looks cleaner and may be even nicer/performant with a Attribute::factory() returning empty default clones.
I wonder what effort would be involved in converting all 'render element' to variables. I've seen it done but it would be easier if variables wasn't so strict on requiring the variables be defined ahead of time. I digress...
Anyways, thoughts?
Comment #124
joelpittetI discussed with @davidhernandez in IRC and I think we are of the same mindset.
A) It's weird we have to do this attribute check and build in the preprocess.
B) No need for preprocess in core (except for tests because we want it to still work).
One blocker for this desired outcome is 'render element'.
But here's what that would look like with datetime_wrapper converted to variables! What a clean preprocess because all the variables map to what the template expects!
Comment #125
davidhernandezYou also have the search_theme() change in there. :)
Comment #126
joelpittetWhoops that was my first attempt before moving hook_theme to variables. Not needed.
The other 'render element's are hard/impossible to change at the moment because they take loop through the element_children() or have variable variables.
Comment #127
joelpittetKinda off topic but #2465399-18: IGNORE: Patch testing issue would be nice and it's green. Allows for variables to be passed through that are not explicitly defined in the hook_theme(). Just a bit less rigid. Food for thought
Comment #128
joelpittetBumping this 9.x to triage since we are in RC for 8.0.x
Comment #129
fgmI guess we could target it for 8.2.x if we keep title|content_attributes marked as deprecated and introducing the new mechanism: this seems to be what minor versions like 8.*.x are about.