DRYML is incompatible with Rails 3 block helpers
Reported by Matt Jones | September 22nd, 2011 @ 11:08 PM | in Hobo 1.3 (Rails 3)
Summary:
The ERB parser used by DRYML doesn't support the new-style Rails
block helpers. Using <% %>
gets you no output,
and using <%= %>
creates invalid ERB.
Rails 3 patches in some changes to Erubis to enable this
behavior; in particular, it avoids using parentheses around
do |args|
clauses.
One can try using the new parser in DRYML by changing one line
in dryml_builder.rb
:
erb = ERB.new(erb_src, nil, trim_mode, "output_buffer")
# changes to
erb = ActionView::TemplateHandlers::ERB.erb_implementation.new(erb_src, :trim => trim_mode)
However, this blows up disastrously when there are procs in ERB
- in other words, anywhere DRYML uses the param
mechanism.
There are additional potential issues (such as switching from
output_buffer
to @output_buffer
) but this
is certainly one of the biggest.
Comments and changes to this ticket
-
Matt Jones September 23rd, 2011 @ 02:14 AM
Some further notes on this:
-
the patched version of Erubis that Rails uses makes use of
@output_buffer
, which isn't even in the right OBJECT when called in the functions intemplate.rb
. I got a page to render by disabling all the taglibs and doing asrc.gsub('@output_buffer', 'output_buffer')
in therender_page
function, but that's not a great solution. -
the patched version triggers the fallback for block helpers (
@output_buffer.append_if_string
) any time it sniffs something that looks vaguely like a block. I got it to stop eating ourproc
calls by changingBLOCK_EXPR
(in erb.rb) to(?<!proc)\s+(do|\{)(\s*\|[^|]*\|)?\s*\Z
, but that requires negative lookbehind which is Ruby 1.9-only. It also still has problems when we create a line that starts with a bunch of brackets / parens and then has a new_context block. For instance, theaccount-page
tag produces this line of ERB:
" } }, }] }, \n :password_confirmation_label => proc { [{}, { :default => proc { |_password_confirmation_label__default_content| new_context { "
(less the quote marks), which turns into utter fail when Rails tacks
@output_buffer.append_if_string=
on the beginning.Need to evaluate this further - maybe we could do our own ERB parser? Or, failing that, fix block helpers when we do the "ERB scriptlets" translation?
-
-
Matt Jones September 25th, 2011 @ 05:11 AM
(from [17011ac522994cf0b69faddd62fa170f96657c49]) [#966] support Rails 3-style block helpers https://github.com/tablatom/hobo/commit/17011ac522994cf0b69faddd62f...
-
Matt Jones September 25th, 2011 @ 05:18 AM
Alright, I've got a reasonable solution (commit above). Several caveats:
-
vanilla Rails complains if you mistakenly enclose a block helper in
<% %>
instead of<%= %>
. The code to support this was the principal roadblock to working with DRYML, so the code doesn't do this. Thus, improperly bracketed block helpers will FAIL SILENTLY. -
standard ERB partials mostly work - but they don't actually access the same set of instance variables as DRYML code does (plain ERB talks to the
TemplateEnvironment
view object). The variables will be the same if they were set in the controller, but changes will not propagate from one to the other. Use:locals
; it's not just a best practice, it's the law! -
replacing ActionView's ERB handler doesn't change Hobo's - very few people will want to do this, but worth noting.
-
-
Tim Griffin October 14th, 2011 @ 04:27 AM
Hi Matt;
WRT to my recent posting on Hobo Users, I just noticed that edge Hobo 1.3 has a broken dev-user-changer. In my own code, I had to override the "<%" occurences with "<%=" to get the <select-menu> to include options. Does this seem right?
(I don't have any other <select-menu> tags in my app so the dev-user-changer is the first I noticed!)
<def tag="select-menu" attrs="options, selected, first-option, first-value, key"> <%= key ||= 'default' %w[options first_option first_value].each do |a| str = t("tags.select_menu.#{key}.#{a}", :default=>'') eval "#{a} = str unless str.blank?" end -%> <select merge-attrs param="default"> <%= selected=this if selected.nil? %> <option value="#{first_value}" unless="&first_option.nil?"><first-option/></option> <do param="options"><%= options_for_select(options, selected) %></do> </select> </def>
-
Tim Griffin October 14th, 2011 @ 04:31 AM
(I see now that I only needed to update the <%= where 'options_for_select' appears, not the others.)
-
Bryan Larsen October 22nd, 2011 @ 09:33 PM
Arg, I didn't see your fix Tim and tracked this down independently. Oops. Now we just need to check to ensure that this same problem isn't elsewhere in Rapid.
-
Bryan Larsen October 22nd, 2011 @ 09:36 PM
(from [865563ecad62d98d4a31d11f802dc76ab41c4802]) [#966] fix dev-user-changer and select-menu bugs exposed by #966 bugfix. https://github.com/tablatom/hobo/commit/865563ecad62d98d4a31d11f802...
-
Bryan Larsen October 25th, 2011 @ 04:06 PM
- State changed from open to resolved
A quick audit of RAPID shows no other bugs of the type Tim found. I'm going to close this ticket and put out an RC PDQ. Reopen if you think there's more to do here.
Please Sign in or create a free account to add a new ticket.
With your very own profile, you can contribute to projects, track your activity, watch tickets, receive and update tickets through your email and much more.
Create your profile
Help contribute to this project by taking a few moments to create your personal profile. Create your profile ยป
People watching this ticket
Referenced by
- 966 DRYML is incompatible with Rails 3 block helpers (from [17011ac522994cf0b69faddd62fa170f96657c49]) [#966] ...