aboutsummaryrefslogtreecommitdiffstats
path: root/actionpack
diff options
context:
space:
mode:
authorJoshua Peek <josh@joshpeek.com>2008-07-06 01:13:15 -0500
committerJoshua Peek <josh@joshpeek.com>2008-07-06 01:13:15 -0500
commit1d8623b42f6249613d39e834a8742b3b143f2aff (patch)
treef8316aab80fd86c15008d218d2a33717ff4b3c74 /actionpack
parent7b9e8ae2734089555e5bfdb9e9c80d92f43551a2 (diff)
downloadrails-1d8623b42f6249613d39e834a8742b3b143f2aff.tar.gz
rails-1d8623b42f6249613d39e834a8742b3b143f2aff.tar.bz2
rails-1d8623b42f6249613d39e834a8742b3b143f2aff.zip
Added local assign keys to compiled method name so two threads evaluating the same template with different locals don't step on top of each other
Diffstat (limited to 'actionpack')
-rw-r--r--actionpack/lib/action_view/renderable.rb8
-rw-r--r--actionpack/lib/action_view/template.rb2
-rw-r--r--actionpack/lib/action_view/template_handlers/compilable.rb25
3 files changed, 9 insertions, 26 deletions
diff --git a/actionpack/lib/action_view/renderable.rb b/actionpack/lib/action_view/renderable.rb
index 2e2fff44c6..3a30e603fe 100644
--- a/actionpack/lib/action_view/renderable.rb
+++ b/actionpack/lib/action_view/renderable.rb
@@ -12,7 +12,7 @@ module ActionView
end
def method
- ['_run', @extension, @method_segment].compact.join('_').to_sym
+ ['_run', @extension, @method_segment, local_assigns_keys].compact.join('_').to_sym
end
private
@@ -28,5 +28,11 @@ module ActionView
@prepared = true
end
end
+
+ def local_assigns_keys
+ if @locals && @locals.any?
+ "locals_#{@locals.keys.map { |k| k.to_s }.sort.join('_')}"
+ end
+ end
end
end
diff --git a/actionpack/lib/action_view/template.rb b/actionpack/lib/action_view/template.rb
index 069d7d57af..5e5ea9b9b9 100644
--- a/actionpack/lib/action_view/template.rb
+++ b/actionpack/lib/action_view/template.rb
@@ -20,7 +20,7 @@ module ActionView #:nodoc:
set_extension_and_file_name
@method_segment = compiled_method_name_file_path_segment
- @locals = locals || {}
+ @locals = (locals && locals.dup) || {}
@handler = self.class.handler_class_for_extension(@extension).new(@view)
end
diff --git a/actionpack/lib/action_view/template_handlers/compilable.rb b/actionpack/lib/action_view/template_handlers/compilable.rb
index d079ef3d15..256d8da031 100644
--- a/actionpack/lib/action_view/template_handlers/compilable.rb
+++ b/actionpack/lib/action_view/template_handlers/compilable.rb
@@ -5,9 +5,6 @@ module ActionView
base.extend ClassMethod
@@mutex = Mutex.new
-
- # Map method names to the compiled local assigns
- @@template_args = {}
end
module ClassMethod
@@ -26,11 +23,7 @@ module ActionView
return false unless recompile_template?(template)
@@mutex.synchronize do
- locals_code = ""
- locals_keys = cache_template_args(template.method, template.locals)
- locals_keys.each do |key|
- locals_code << "#{key} = local_assigns[:#{key}];"
- end
+ locals_code = template.locals.keys.map { |key| "#{key} = local_assigns[:#{key}];" }.join
source = <<-end_src
def #{template.method}(local_assigns)
@@ -69,25 +62,9 @@ module ActionView
# Always recompile inline templates
return true if template.is_a?(InlineTemplate)
- # Unless local assigns support, recompile
- return true unless supports_local_assigns?(template.method, template.locals)
-
# Otherwise, use compiled method
return false
end
-
- def cache_template_args(render_symbol, local_assigns)
- @@template_args[render_symbol] ||= {}
- locals_keys = @@template_args[render_symbol].keys | local_assigns.keys
- @@template_args[render_symbol] = locals_keys.inject({}) { |h, k| h[k] = true; h }
- locals_keys
- end
-
- # Return true if the given template was compiled for a superset of the keys in local_assigns
- def supports_local_assigns?(render_symbol, local_assigns)
- local_assigns.empty? ||
- ((args = @@template_args[render_symbol]) && local_assigns.all? { |k,_| args.has_key?(k) })
- end
end
end
end