phoenix_slime icon indicating copy to clipboard operation
phoenix_slime copied to clipboard

String interpolation in tags nested in variables does not work

Open MajronMan opened this issue 7 years ago • 8 comments

Environment:

  • Erlang/OTP 20
  • Elixir 1.5.1
  • Phoenix 1.3.0
  • Phoenix HTML 2.10.4
  • Phoenix Slime 0.9.0
  • Slime 0.16.0
  • System 4.12.8-1-ARCH

Expected behaviour

String interpolation in input value works like without interpolation, e.g.

- foo = "bar"

- form_ok = Phoenix.HTML.Tag.content_tag(:form) do
  input name="test" value="val"

p "#{foo}"

= form_ok

Renders

<p>bar</p>
<form>
  <input name="test" value="val">
</form>

Actual behaviour

- foo = "bar"

- form_not_ok = Phoenix.HTML.Tag.content_tag(:form) do
  input name="test" value="#{foo}"

p "#{foo}"

= form_not_ok

Renders

<input name="test"<p>bar</p>
<form>
  <input name="test" value="bar">
</form>     

MajronMan avatar Aug 18 '17 14:08 MajronMan

@MajronMan it may be that I don't have much ☕️ in me yet but are these two examples not different? The first doesn't appear to include interpolation.

Do you have code somewhere I can peek at? If not, I'll try to throw together a simple Slime application (sans Phoenix) and see if we can narrow it down. @Rakoth I think this may be an issue with the parser, wanted to give you a heads up 👍

doomspork avatar Aug 23 '17 15:08 doomspork

@doomspork You might be right and it's not a perfect example, I just wanted to show that the case is certainly the interpolation since it's the only difference between those two pieces of code.

I stumbled upon this bug in rather complex circumstances and I doubt they are worth describing in detail, but the main idea was to reuse a form created by my own function (to add CSRF token etc.) with inputs populated with values passed to the template by Phoenix View's assigns. Investigation enabled me to produce this simple example above.

MajronMan avatar Aug 23 '17 16:08 MajronMan

@MajronMan do you have that code public?

doomspork avatar Aug 23 '17 17:08 doomspork

@MajronMan Hi! Could you reproduce this issue with slime 1.0?

Rakoth avatar Aug 23 '17 17:08 Rakoth

@doomspork Unfortunately I can't share this code :(

@Rakoth I don't know how to do it without using Phoenix Tag and I used this library, but I will try to do so tomorrow (I am in different timezone so it's evening for me)

MajronMan avatar Aug 23 '17 18:08 MajronMan

@MajronMan you could just add {:slime, "~> 1.0", override: true} into your project's deps

Rakoth avatar Aug 24 '17 06:08 Rakoth

@Rakoth I created a repo with slime 1.0 and the bug is still there https://github.com/MajronMan/slime_bug

MajronMan avatar Aug 24 '17 09:08 MajronMan

Thanks @MajronMan it helped a lot! I narrowed it down to a very strange behaviour of EEx:

<h1>header</h1>
<% foo = "bar" %>
<% form_not_ok = Phoenix.HTML.Tag.content_tag(:form) do %>
  test
  <% a = "baz" %>
  <div id="<%= a %>"></div>
<% end %>
<%= form_not_ok %>

renders to


  test
<form>
  test
  <div id="baz"></div>
</form>

Note repeated test string and missing <h1>. There is some problem with <% a = "baz" %> part. Since Slime uses eex representation underhood and attribute interpolation code compiles to similar eex template we are affected by this issue. I will try to find a workaround for this case.

Rakoth avatar Aug 24 '17 14:08 Rakoth