haml 4.0.7 → 5.2.2
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +5 -5
- data/.github/workflows/test.yml +36 -0
- data/.gitignore +19 -0
- data/.gitmodules +3 -0
- data/.yardopts +2 -3
- data/CHANGELOG.md +146 -4
- data/FAQ.md +4 -14
- data/Gemfile +16 -0
- data/MIT-LICENSE +2 -2
- data/README.md +90 -47
- data/REFERENCE.md +160 -74
- data/Rakefile +44 -63
- data/TODO +24 -0
- data/benchmark.rb +70 -0
- data/haml.gemspec +45 -0
- data/lib/haml/.gitattributes +1 -0
- data/lib/haml/attribute_builder.rb +219 -0
- data/lib/haml/attribute_compiler.rb +237 -0
- data/lib/haml/attribute_parser.rb +150 -0
- data/lib/haml/buffer.rb +12 -175
- data/lib/haml/compiler.rb +110 -320
- data/lib/haml/engine.rb +34 -41
- data/lib/haml/error.rb +28 -24
- data/lib/haml/escapable.rb +77 -0
- data/lib/haml/exec.rb +38 -20
- data/lib/haml/filters.rb +22 -27
- data/lib/haml/generator.rb +42 -0
- data/lib/haml/helpers/action_view_extensions.rb +4 -2
- data/lib/haml/helpers/action_view_mods.rb +45 -60
- data/lib/haml/helpers/action_view_xss_mods.rb +2 -0
- data/lib/haml/helpers/safe_erubi_template.rb +20 -0
- data/lib/haml/helpers/safe_erubis_template.rb +5 -1
- data/lib/haml/helpers/xss_mods.rb +23 -13
- data/lib/haml/helpers.rb +134 -89
- data/lib/haml/options.rb +63 -69
- data/lib/haml/parser.rb +319 -227
- data/lib/haml/plugin.rb +54 -0
- data/lib/haml/railtie.rb +43 -12
- data/lib/haml/sass_rails_filter.rb +18 -4
- data/lib/haml/template/options.rb +13 -2
- data/lib/haml/template.rb +13 -6
- data/lib/haml/temple_engine.rb +124 -0
- data/lib/haml/temple_line_counter.rb +30 -0
- data/lib/haml/util.rb +83 -202
- data/lib/haml/version.rb +3 -1
- data/lib/haml.rb +2 -0
- data/yard/default/.gitignore +1 -0
- data/yard/default/fulldoc/html/css/common.sass +15 -0
- data/yard/default/layout/html/footer.erb +12 -0
- metadata +73 -115
- data/lib/haml/template/plugin.rb +0 -41
- data/test/engine_test.rb +0 -2013
- data/test/erb/_av_partial_1.erb +0 -12
- data/test/erb/_av_partial_2.erb +0 -8
- data/test/erb/action_view.erb +0 -62
- data/test/erb/standard.erb +0 -55
- data/test/filters_test.rb +0 -254
- data/test/gemfiles/Gemfile.rails-3.0.x +0 -5
- data/test/gemfiles/Gemfile.rails-3.1.x +0 -6
- data/test/gemfiles/Gemfile.rails-3.2.x +0 -5
- data/test/gemfiles/Gemfile.rails-4.0.x +0 -5
- data/test/haml-spec/LICENSE +0 -14
- data/test/haml-spec/README.md +0 -106
- data/test/haml-spec/lua_haml_spec.lua +0 -38
- data/test/haml-spec/perl_haml_test.pl +0 -81
- data/test/haml-spec/ruby_haml_test.rb +0 -23
- data/test/haml-spec/tests.json +0 -660
- data/test/helper_test.rb +0 -583
- data/test/markaby/standard.mab +0 -52
- data/test/mocks/article.rb +0 -6
- data/test/parser_test.rb +0 -105
- data/test/results/content_for_layout.xhtml +0 -12
- data/test/results/eval_suppressed.xhtml +0 -9
- data/test/results/helpers.xhtml +0 -70
- data/test/results/helpful.xhtml +0 -10
- data/test/results/just_stuff.xhtml +0 -70
- data/test/results/list.xhtml +0 -12
- data/test/results/nuke_inner_whitespace.xhtml +0 -40
- data/test/results/nuke_outer_whitespace.xhtml +0 -148
- data/test/results/original_engine.xhtml +0 -20
- data/test/results/partial_layout.xhtml +0 -5
- data/test/results/partial_layout_erb.xhtml +0 -5
- data/test/results/partials.xhtml +0 -21
- data/test/results/render_layout.xhtml +0 -3
- data/test/results/silent_script.xhtml +0 -74
- data/test/results/standard.xhtml +0 -162
- data/test/results/tag_parsing.xhtml +0 -23
- data/test/results/very_basic.xhtml +0 -5
- data/test/results/whitespace_handling.xhtml +0 -90
- data/test/template_test.rb +0 -354
- data/test/templates/_av_partial_1.haml +0 -9
- data/test/templates/_av_partial_1_ugly.haml +0 -9
- data/test/templates/_av_partial_2.haml +0 -5
- data/test/templates/_av_partial_2_ugly.haml +0 -5
- data/test/templates/_layout.erb +0 -3
- data/test/templates/_layout_for_partial.haml +0 -3
- data/test/templates/_partial.haml +0 -8
- data/test/templates/_text_area.haml +0 -3
- data/test/templates/_text_area_helper.html.haml +0 -4
- data/test/templates/action_view.haml +0 -47
- data/test/templates/action_view_ugly.haml +0 -47
- data/test/templates/breakage.haml +0 -8
- data/test/templates/content_for_layout.haml +0 -8
- data/test/templates/eval_suppressed.haml +0 -11
- data/test/templates/helpers.haml +0 -55
- data/test/templates/helpful.haml +0 -11
- data/test/templates/just_stuff.haml +0 -85
- data/test/templates/list.haml +0 -12
- data/test/templates/nuke_inner_whitespace.haml +0 -32
- data/test/templates/nuke_outer_whitespace.haml +0 -144
- data/test/templates/original_engine.haml +0 -17
- data/test/templates/partial_layout.haml +0 -3
- data/test/templates/partial_layout_erb.erb +0 -4
- data/test/templates/partialize.haml +0 -1
- data/test/templates/partials.haml +0 -12
- data/test/templates/render_layout.haml +0 -2
- data/test/templates/silent_script.haml +0 -45
- data/test/templates/standard.haml +0 -43
- data/test/templates/standard_ugly.haml +0 -43
- data/test/templates/tag_parsing.haml +0 -21
- data/test/templates/very_basic.haml +0 -4
- data/test/templates/whitespace_handling.haml +0 -87
- data/test/test_helper.rb +0 -81
- data/test/util_test.rb +0 -63
data/lib/haml/buffer.rb
CHANGED
@@ -1,3 +1,5 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
1
3
|
module Haml
|
2
4
|
# This class is used only internally. It holds the buffer of HTML that
|
3
5
|
# is eventually output as the resulting document.
|
@@ -90,7 +92,8 @@ module Haml
|
|
90
92
|
def initialize(upper = nil, options = {})
|
91
93
|
@active = true
|
92
94
|
@upper = upper
|
93
|
-
@options =
|
95
|
+
@options = Options.buffer_defaults
|
96
|
+
@options = @options.merge(options) unless options.empty?
|
94
97
|
@buffer = new_encoded_string
|
95
98
|
@tabulation = 0
|
96
99
|
|
@@ -115,8 +118,8 @@ module Haml
|
|
115
118
|
text.sub!(tabs, '') if dont_tab_up
|
116
119
|
end
|
117
120
|
|
118
|
-
@buffer << text
|
119
121
|
@real_tabs += tab_change
|
122
|
+
@buffer << text
|
120
123
|
end
|
121
124
|
|
122
125
|
# Modifies the indentation of the document.
|
@@ -127,85 +130,6 @@ module Haml
|
|
127
130
|
@real_tabs += tab_change
|
128
131
|
end
|
129
132
|
|
130
|
-
Haml::Util.def_static_method(self, :format_script, [:result],
|
131
|
-
:preserve_script, :in_tag, :preserve_tag, :escape_html,
|
132
|
-
:nuke_inner_whitespace, :interpolated, :ugly, <<RUBY)
|
133
|
-
<% # Escape HTML here so that the safety of the string is preserved in Rails
|
134
|
-
result_name = escape_html ? "html_escape(result.to_s)" : "result.to_s" %>
|
135
|
-
<% unless ugly %>
|
136
|
-
# If we're interpolated,
|
137
|
-
# then the custom tabulation is handled in #push_text.
|
138
|
-
# The easiest way to avoid it here is to reset @tabulation.
|
139
|
-
<% if interpolated %>
|
140
|
-
old_tabulation = @tabulation
|
141
|
-
@tabulation = 0
|
142
|
-
<% end %>
|
143
|
-
|
144
|
-
<% if !(in_tag && preserve_tag && !nuke_inner_whitespace) %>
|
145
|
-
tabulation = @real_tabs
|
146
|
-
<% end %>
|
147
|
-
result = <%= result_name %>.<% if nuke_inner_whitespace %>strip<% else %>rstrip<% end %>
|
148
|
-
<% else %>
|
149
|
-
result = <%= result_name %><% if nuke_inner_whitespace %>.strip<% end %>
|
150
|
-
<% end %>
|
151
|
-
|
152
|
-
<% if preserve_tag %>
|
153
|
-
result = Haml::Helpers.preserve(result)
|
154
|
-
<% elsif preserve_script %>
|
155
|
-
result = Haml::Helpers.find_and_preserve(result, options[:preserve])
|
156
|
-
<% end %>
|
157
|
-
|
158
|
-
<% if ugly %>
|
159
|
-
fix_textareas!(result) if toplevel? && result.include?('<textarea')
|
160
|
-
return result
|
161
|
-
<% else %>
|
162
|
-
<% if !(in_tag && preserve_tag && !nuke_inner_whitespace) %>
|
163
|
-
has_newline = result.include?("\\n")
|
164
|
-
<% end %>
|
165
|
-
|
166
|
-
<% if in_tag && !nuke_inner_whitespace %>
|
167
|
-
<% unless preserve_tag %> if !has_newline <% end %>
|
168
|
-
@real_tabs -= 1
|
169
|
-
<% if interpolated %> @tabulation = old_tabulation <% end %>
|
170
|
-
return result
|
171
|
-
<% unless preserve_tag %> end <% end %>
|
172
|
-
<% end %>
|
173
|
-
|
174
|
-
<% if !(in_tag && preserve_tag && !nuke_inner_whitespace) %>
|
175
|
-
# Precompiled tabulation may be wrong
|
176
|
-
<% if !interpolated && !in_tag %>
|
177
|
-
result = tabs + result if @tabulation > 0
|
178
|
-
<% end %>
|
179
|
-
|
180
|
-
if has_newline
|
181
|
-
result = result.gsub "\\n", "\\n" + tabs(tabulation)
|
182
|
-
|
183
|
-
# Add tabulation if it wasn't precompiled
|
184
|
-
<% if in_tag && !nuke_inner_whitespace %> result = tabs(tabulation) + result <% end %>
|
185
|
-
end
|
186
|
-
|
187
|
-
fix_textareas!(result) if toplevel? && result.include?('<textarea')
|
188
|
-
|
189
|
-
<% if in_tag && !nuke_inner_whitespace %>
|
190
|
-
result = "\\n\#{result}\\n\#{tabs(tabulation-1)}"
|
191
|
-
@real_tabs -= 1
|
192
|
-
<% end %>
|
193
|
-
<% if interpolated %> @tabulation = old_tabulation <% end %>
|
194
|
-
result
|
195
|
-
<% end %>
|
196
|
-
<% end %>
|
197
|
-
RUBY
|
198
|
-
|
199
|
-
def attributes(class_id, obj_ref, *attributes_hashes)
|
200
|
-
attributes = class_id
|
201
|
-
attributes_hashes.each do |old|
|
202
|
-
self.class.merge_attrs(attributes, Hash[old.map {|k, v| [k.to_s, v]}])
|
203
|
-
end
|
204
|
-
self.class.merge_attrs(attributes, parse_object_ref(obj_ref)) if obj_ref
|
205
|
-
Compiler.build_attributes(
|
206
|
-
html?, @options[:attr_wrapper], @options[:escape_attrs], @options[:hyphenate_data_attrs], attributes)
|
207
|
-
end
|
208
|
-
|
209
133
|
# Remove the whitespace from the right side of the buffer string.
|
210
134
|
# Doesn't do anything if we're at the beginning of a capture_haml block.
|
211
135
|
def rstrip!
|
@@ -217,50 +141,6 @@ RUBY
|
|
217
141
|
buffer << buffer.slice!(capture_position..-1).rstrip
|
218
142
|
end
|
219
143
|
|
220
|
-
# Merges two attribute hashes.
|
221
|
-
# This is the same as `to.merge!(from)`,
|
222
|
-
# except that it merges id, class, and data attributes.
|
223
|
-
#
|
224
|
-
# ids are concatenated with `"_"`,
|
225
|
-
# and classes are concatenated with `" "`.
|
226
|
-
# data hashes are simply merged.
|
227
|
-
#
|
228
|
-
# Destructively modifies both `to` and `from`.
|
229
|
-
#
|
230
|
-
# @param to [{String => String}] The attribute hash to merge into
|
231
|
-
# @param from [{String => #to_s}] The attribute hash to merge from
|
232
|
-
# @return [{String => String}] `to`, after being merged
|
233
|
-
def self.merge_attrs(to, from)
|
234
|
-
from['id'] = Compiler.filter_and_join(from['id'], '_') if from['id']
|
235
|
-
if to['id'] && from['id']
|
236
|
-
to['id'] << '_' << from.delete('id').to_s
|
237
|
-
elsif to['id'] || from['id']
|
238
|
-
from['id'] ||= to['id']
|
239
|
-
end
|
240
|
-
|
241
|
-
from['class'] = Compiler.filter_and_join(from['class'], ' ') if from['class']
|
242
|
-
if to['class'] && from['class']
|
243
|
-
# Make sure we don't duplicate class names
|
244
|
-
from['class'] = (from['class'].to_s.split(' ') | to['class'].split(' ')).sort.join(' ')
|
245
|
-
elsif to['class'] || from['class']
|
246
|
-
from['class'] ||= to['class']
|
247
|
-
end
|
248
|
-
|
249
|
-
from_data = from.delete('data') || {}
|
250
|
-
to_data = to.delete('data') || {}
|
251
|
-
|
252
|
-
# forces to_data & from_data into a hash
|
253
|
-
from_data = { nil => from_data } unless from_data.is_a?(Hash)
|
254
|
-
to_data = { nil => to_data } unless to_data.is_a?(Hash)
|
255
|
-
|
256
|
-
merged_data = to_data.merge(from_data)
|
257
|
-
|
258
|
-
to['data'] = merged_data unless merged_data.empty?
|
259
|
-
to.merge!(from)
|
260
|
-
end
|
261
|
-
|
262
|
-
private
|
263
|
-
|
264
144
|
# Works like #{find_and_preserve}, but allows the first newline after a
|
265
145
|
# preserved opening tag to remain unencoded, and then outdents the content.
|
266
146
|
# This change was motivated primarily by the change in Rails 3.2.3 to emit
|
@@ -270,6 +150,8 @@ RUBY
|
|
270
150
|
# @since Haml 4.0.1
|
271
151
|
# @private
|
272
152
|
def fix_textareas!(input)
|
153
|
+
return input unless input.include?('<textarea'.freeze)
|
154
|
+
|
273
155
|
pattern = /<(textarea)([^>]*)>(\n|
)(.*?)<\/textarea>/im
|
274
156
|
input.gsub!(pattern) do |s|
|
275
157
|
match = pattern.match(s)
|
@@ -281,16 +163,13 @@ RUBY
|
|
281
163
|
end
|
282
164
|
"<#{match[1]}#{match[2]}>\n#{content}</#{match[1]}>"
|
283
165
|
end
|
166
|
+
input
|
284
167
|
end
|
285
168
|
|
286
|
-
|
287
|
-
|
288
|
-
|
289
|
-
|
290
|
-
else
|
291
|
-
def new_encoded_string
|
292
|
-
"".encode(Encoding.find(options[:encoding]))
|
293
|
-
end
|
169
|
+
private
|
170
|
+
|
171
|
+
def new_encoded_string
|
172
|
+
"".encode(options[:encoding])
|
294
173
|
end
|
295
174
|
|
296
175
|
@@tab_cache = {}
|
@@ -299,47 +178,5 @@ RUBY
|
|
299
178
|
tabs = [count + @tabulation, 0].max
|
300
179
|
@@tab_cache[tabs] ||= ' ' * tabs
|
301
180
|
end
|
302
|
-
|
303
|
-
# Takes an array of objects and uses the class and id of the first
|
304
|
-
# one to create an attributes hash.
|
305
|
-
# The second object, if present, is used as a prefix,
|
306
|
-
# just like you can do with `dom_id()` and `dom_class()` in Rails
|
307
|
-
def parse_object_ref(ref)
|
308
|
-
prefix = ref[1]
|
309
|
-
ref = ref[0]
|
310
|
-
# Let's make sure the value isn't nil. If it is, return the default Hash.
|
311
|
-
return {} if ref.nil?
|
312
|
-
class_name =
|
313
|
-
if ref.respond_to?(:haml_object_ref)
|
314
|
-
ref.haml_object_ref
|
315
|
-
else
|
316
|
-
underscore(ref.class)
|
317
|
-
end
|
318
|
-
ref_id =
|
319
|
-
if ref.respond_to?(:to_key)
|
320
|
-
key = ref.to_key
|
321
|
-
key.join('_') unless key.nil?
|
322
|
-
else
|
323
|
-
ref.id
|
324
|
-
end
|
325
|
-
id = "#{class_name}_#{ref_id || 'new'}"
|
326
|
-
if prefix
|
327
|
-
class_name = "#{ prefix }_#{ class_name}"
|
328
|
-
id = "#{ prefix }_#{ id }"
|
329
|
-
end
|
330
|
-
|
331
|
-
{'id' => id, 'class' => class_name}
|
332
|
-
end
|
333
|
-
|
334
|
-
# Changes a word from camel case to underscores.
|
335
|
-
# Based on the method of the same name in Rails' Inflector,
|
336
|
-
# but copied here so it'll run properly without Rails.
|
337
|
-
def underscore(camel_cased_word)
|
338
|
-
camel_cased_word.to_s.gsub(/::/, '_').
|
339
|
-
gsub(/([A-Z]+)([A-Z][a-z])/,'\1_\2').
|
340
|
-
gsub(/([a-z\d])([A-Z])/,'\1_\2').
|
341
|
-
tr("-", "_").
|
342
|
-
downcase
|
343
|
-
end
|
344
181
|
end
|
345
182
|
end
|