liquid icon indicating copy to clipboard operation
liquid copied to clipboard

Comparison operators are whitespace-sensitive

Open Shadowen opened this issue 8 years ago • 8 comments

I was messing around in Jekyll with Liquid and discovered this weird behaviour when I hit auto-format on an HTML file:

{% assign foo = "bar" %}
{% if foo == "bar" %}
  true
{% else %}
  false
{% endif %}

gives the result true, whereas

{% assign foo = "bar" %}
{% if foo=="bar" %}
  true
{% else %}
  false
{% endif %}

gives the result false.

Furthermore,

{% assign foo = "" %}
{% if foo=="bar" %}
  true
{% else %}
  false
{% endif %}

gives the result true, as though Liquid is evaluating against the empty string.

Can anyone replicate this? Is this documented (and I missed it)? I can't seem to find any notes on how whitespace is relevant to Liquid, and I would expect it to obey the same whitespace rules as HTML (ie. ignore all unnecessary whitespace). #428 relevant?

Shadowen avatar Jul 30 '15 21:07 Shadowen

The problem is that foo=="bar" gets parsed as a single Liquid::QuotedFragment in Liquid::If::Syntax as if it were 'foo=="bar"' due to liquid's lax expression parsing. It will behave as expected with the strict error mode but not the lax error mode.

I can replicate this, but I don't think we were previously aware of this liquid quirk.

dylanahsmith avatar Jul 31 '15 01:07 dylanahsmith

@Shadowen: This should be fixed in Jekyll 3, where the strict parser is the default behaviour.

fw42 avatar Jul 31 '15 01:07 fw42

Wow, this is one of my favourite quirks yet. I thought previously that the lax parser was at least whitespace-invariant.

trishume avatar Jul 31 '15 13:07 trishume

I vote to mark this #wontfix in the lax parser since I bet there are templates that will break if we do :crying_cat_face:.

pushrax avatar Jul 31 '15 18:07 pushrax

This should probably also work in warn mode, since it parses strictly then falls back to lax mode only if it can't be strictly parsed. So I guess warn mode might be the most lax mode.

dylanahsmith avatar Jul 31 '15 19:07 dylanahsmith

We should run a template comparator job with the strict vs lax parser to test if this actually affects any production templates. It's quite possible it doesn't affect many, and if it does fixing this might not break them.

trishume avatar Jul 31 '15 19:07 trishume

Still not fixed. This is not a quirk. It is a timewasting bug. This is year 2022. I'll check back in another 5 years.

schien-dong avatar Apr 17 '22 20:04 schien-dong

Yes, it is a bug, but we need to consider any existing liquid code that could break from fixing it.

The strict parser ended up acting like another version of liquid, which allowed it to essentially fix this, so adopting the strict parser can be a way of avoiding this problem where it is possible. This issue was raised in the context of Jekyll, which now defaults to warn mode, which I believe avoids this issue.

In the context of Shopify, I believe Shopify parses sections using the strict parser. So, if I understand correctly, you would be able to adopt those in order to avoid this issue in Shopify.

dylanahsmith avatar Apr 19 '22 14:04 dylanahsmith