Problem/Motivation
Follow-up to #2330731: Attribute::addClass() adds empty class to cover more cases and add the corresponding test coverage.
#2330731: Attribute::addClass() adds empty class fixed the case of Attribute->addClass()
(with no arguments) resulting in class=""
, but there are still several other cases not accounted for that will result in class=""
.
The main usage case in core is when adding classes from Twig template and using ternary operators. If not specified in the ternary, a false value returns an empty string (http://twig.sensiolabs.org/doc/templates.html#other-operators). Attribute is still returning an empty class attribute when it's passed in an empty string.
Proposed resolution
Fix it.
Remaining tasks
Patch + tests.
User interface changes
n/a
API changes
n/a
Comment | File | Size | Author |
---|---|---|---|
#20 | 2336355.20.patch | 6.05 KB | alexpott |
#20 | 16-20-interdiff.txt | 1.43 KB | alexpott |
#16 | 2336355.16.patch | 6.04 KB | alexpott |
#16 | 14-16-interdiff.txt | 1.33 KB | alexpott |
#14 | 2336355.14.patch | 5.8 KB | alexpott |
Comments
Comment #1
star-szrAdding a bit more information to the summary.
Comment #2
star-szrHere's one proposed fix anyway. I know in the original addClass/removeClass issue we didn't want to add array_filter() on print. This is just modifying the addClass(), not on print.
We may need another issue to address what happens when you removeClass() all the classes ;)
Comment #4
RainbowArrayThis looks good to me. Tests seem to be set up correctly. Pretty straightforward. Let's get this in, so we can move forward on other preprocess conversions. We can file another issue for remove classes if necessary.
Comment #5
alexpottLet's just do one array_filter()... we can move
$classes = array_filter($classes);
outside the loop.Comment #6
star-szrGood point!
Comment #7
star-szrThis is blocking and #5 has been addressed so I'm going to move this back to RTBC per #4.
Comment #8
alexpottWhy is AttributeArray not protecting us from this?
Comment #9
star-szrI'll see if I can do another take on this by overriding render in AttributeArray.
Comment #10
alexpottOops - I already did that :(
How about something like the patch attached - this means we only do the filtering and uniqueness once per ArrayAttribute and on render - plus all array attributes get this benefit.
Note that I didn't push these change to AttributeValueBase::render() is because it breaks expectations around code like this:
The first print will output
alt=""
the second print will output nothing. This is tested in AttributesTest (btw AttributesTest vs AttributeTest :) that's nuts).Personally I feel the the ability to output alt="" and prevent class="" are kind of contrary expectations.
No interdiff because it is a new approach.
Comment #11
alexpottRefined the approach so that ArrayAttribute does not have a custom render.
Comment #12
star-szrOkay that looks much better than anything I would have come up with. Thank you so much @alexpott. removeClass() is also fixed with this patch!
Comment #13
alexpott@Cottser noticed an extra word
Comment #14
alexpottlol - thanks @Cottser
Comment #15
joelpittetAwesome, this was exactly the way I was going on Friday, but I got stuck in trying to debug the UnitTest failures... then gave up :(
Didn't think to abstract out that exception for alt tags, nice!
This is great, actually testing the output and not the structure.
Not sure why this array_values() is needed? Secret sauce?
Comment #16
alexpottRe #15.3 because it reindexes the array. So if the values array is
'bb', 'aa'
if you remove'bb'
then the values array is'aa'
and if you var_dump() it it will bearray(0 => 'aa')
notarray(1 => 'aa')
.Patch adds a comments to explain and show where test coverage is. Leaving at RTBC since this just adds clarification.
Comment #17
star-szrThanks @alexpott! I was wondering about that too, makes sense.
Comment #18
joelpittetAh thanks for the clarification, yes still RTBC:) And now we have clean indexes too!
Comment #19
davidhernandezCottser and I were discussing this change on IRC and were curious about what affect on performance it might have. I did some profiling. I tested many times with a custom page that displays teasers for 100 nodes. I also tested a lot on just one node page. We have a few of the preprocess changes already in, including node (Thanks, Alex!) and that template alone has three calls to addClass in it. The numbers I'm seeing fluctuate between 0.5% slower and 0.5% faster, though the majority of runs were in the positive direction. I assume most of it is the margin of error. I'd, unscientifically, call the mode to be around 0.1% faster.
Comment #20
alexpottImproved constant name after discussions with @catch. This class is fully tested by AttributeTest and AttributesTest we should merge them into a single AttributeTest since Attribute is the class under test. Leaving at rtbc since this is a very minor change.
re #19 nice work - this is a patch that will keep on giving though - as we ramp up the use of addClass its affect will be bigger.
Comment #21
star-szr+1, that name makes more sense to me because I think we were saying it could print for NULL, FALSE, etc. as well, not just empty strings.
Comment #22
catchCommitted/pushed to 8.0.x, thanks!