1
0
Fork 0
mirror of https://github.com/haml/haml.git synced 2022-11-09 12:33:31 -05:00

[Haml] [html2haml] Transform inline ERB into Ruby interpolation.

This commit is contained in:
Nathan Weizenbaum 2009-10-05 16:24:38 -07:00
parent ff0bdd254c
commit 0138b212c5
3 changed files with 59 additions and 2 deletions

View file

@ -40,6 +40,20 @@ including the line number and the offending character.
The same is true for inline ERB when running in ERB mode. The same is true for inline ERB when running in ERB mode.
`<p><%= foo %></p>` will now become `%p= foo`. `<p><%= foo %></p>` will now become `%p= foo`.
* ERB included within text is now transformed into Ruby interpolation.
For example:
<p>
Foo <%= bar %> baz!
Flip <%= bang %>.
</p>
is now transformed into:
%p
Foo #{bar} baz!
Flip #{bang}.
* Attributes are now output in a more-standard format, * Attributes are now output in a more-standard format,
without spaces within the curly braces without spaces within the curly braces
(e.g. `%p{:foo => "bar"}` as opposed to `%p{ :foo => "bar" }`). (e.g. `%p{:foo => "bar"}` as opposed to `%p{ :foo => "bar" }`).

View file

@ -9,12 +9,34 @@ module Haml
# A module containing utility methods that every Hpricot node # A module containing utility methods that every Hpricot node
# should have. # should have.
module Node module Node
# Whether this node has already been converted to Haml.
# Only used for text nodes and elements.
#
# @return [Boolean]
attr_accessor :converted_to_haml
# Returns the Haml representation of the given node. # Returns the Haml representation of the given node.
# #
# @param tabs [Fixnum] The indentation level of the resulting Haml. # @param tabs [Fixnum] The indentation level of the resulting Haml.
# @option options (see Haml::HTML#initialize) # @option options (see Haml::HTML#initialize)
def to_haml(tabs, options) def to_haml(tabs, options)
parse_text(self.to_s, tabs) return "" if converted_to_haml || to_s.strip.empty?
text = uninterp(self.to_s)
node = next_node
while node.is_a?(::Hpricot::Elem) && node.name == "haml:loud"
node.converted_to_haml = true
text << '#{' <<
CGI.unescapeHTML(node.inner_text).gsub(/\n\s*/, ' ').strip << '}'
if node.next_node.is_a?(::Hpricot::Text)
node = node.next_node
text << uninterp(node.to_s)
node.converted_to_haml = true
end
node = node.next_node
end
return parse_text_with_interpolation(text, tabs)
end end
private private
@ -23,9 +45,16 @@ module Haml
' ' * tabs ' ' * tabs
end end
def uninterp(text)
text.gsub('#{', '\#{') #'
end
def parse_text(text, tabs) def parse_text(text, tabs)
parse_text_with_interpolation(uninterp(text), tabs)
end
def parse_text_with_interpolation(text, tabs)
text.strip! text.strip!
text.gsub!('#{', '\#{') #'
return "" if text.empty? return "" if text.empty?
text.split("\n").map do |line| text.split("\n").map do |line|
@ -165,6 +194,8 @@ module Haml
class ::Hpricot::Elem class ::Hpricot::Elem
# @see Haml::HTML::Node#to_haml # @see Haml::HTML::Node#to_haml
def to_haml(tabs, options) def to_haml(tabs, options)
return "" if converted_to_haml
output = "#{tabulate(tabs)}" output = "#{tabulate(tabs)}"
if options[:erb] && name[0...5] == 'haml:' if options[:erb] && name[0...5] == 'haml:'
return output + send("haml_tag_#{name[5..-1]}", CGI.unescapeHTML(self.inner_text)) return output + send("haml_tag_#{name[5..-1]}", CGI.unescapeHTML(self.inner_text))

View file

@ -122,6 +122,18 @@ HAML
HTML HTML
end end
def test_erb_in_line
assert_equal 'foo bar #{baz}', render_erb('foo bar <%= baz %>')
assert_equal 'foo bar #{baz}! Bang.', render_erb('foo bar <%= baz %>! Bang.')
end
def test_erb_multi_in_line
assert_equal('foo bar #{baz}! Bang #{bop}.',
render_erb('foo bar <%= baz %>! Bang <%= bop %>.'))
assert_equal('foo bar #{baz}#{bop}!',
render_erb('foo bar <%= baz %><%= bop %>!'))
end
def test_erb_with_html_special_chars def test_erb_with_html_special_chars
assert_equal '= 3 < 5 ? "OK" : "Your computer is b0rken"', assert_equal '= 3 < 5 ? "OK" : "Your computer is b0rken"',
render_erb('<%= 3 < 5 ? "OK" : "Your computer is b0rken" %>') render_erb('<%= 3 < 5 ? "OK" : "Your computer is b0rken" %>')