diff --git a/doc-src/HAML_CHANGELOG.md b/doc-src/HAML_CHANGELOG.md index 1f8d3ddf..22bb15a8 100644 --- a/doc-src/HAML_CHANGELOG.md +++ b/doc-src/HAML_CHANGELOG.md @@ -12,6 +12,9 @@ * Fixed a bug in outer-whitespace nuking where whitespace-only Ruby strings blocked whitespace nuking beyond them. +* Use `ensure` to protect the resetting of the Haml output buffer + against exceptions that are raised within the compiled Haml code. + ## [2.2.10](http://github.com/nex3/haml/commit/2.2.10) * Fixed a bug where elements with dynamic attributes and no content diff --git a/lib/haml/engine.rb b/lib/haml/engine.rb index 607fb136..5fdb5640 100644 --- a/lib/haml/engine.rb +++ b/lib/haml/engine.rb @@ -174,15 +174,13 @@ module Haml @haml_buffer = buffer end - str = eval(precompiled + ";" + precompiled_method_return_value, + eval(precompiled + ";" + precompiled_method_return_value, scope, @options[:filename], @options[:line]) - + ensure # Get rid of the current buffer scope_object.instance_eval do @haml_buffer = buffer.upper end - - str end alias_method :to_html, :render diff --git a/lib/haml/precompiler.rb b/lib/haml/precompiler.rb index ace5739c..ae47f41f 100644 --- a/lib/haml/precompiler.rb +++ b/lib/haml/precompiler.rb @@ -92,14 +92,17 @@ module Haml # Returns the precompiled string with the preamble and postamble def precompiled_with_ambles(local_names) preamble = < scope) + assert(false, "Expected exception") + rescue Exception + assert_nil(scope.send(:haml_buffer)) + end + + def test_def_method_haml_buffer_gets_reset_even_with_exception + scope = Object.new + engine("- raise Haml::Error").def_method(scope, :render) + scope.render + assert(false, "Expected exception") + rescue Exception + assert_nil(scope.send(:haml_buffer)) + end + + def test_render_proc_haml_buffer_gets_reset_even_with_exception + scope = Object.new + proc = engine("- raise Haml::Error").render_proc(scope) + proc.call + assert(false, "Expected exception") + rescue Exception + assert_nil(scope.send(:haml_buffer)) + end + def test_ugly_true assert_equal("
\n
\n

hello world

\n
\n
\n", render("#outer\n #inner\n %p hello world", :ugly => true))