diff options
-rw-r--r-- | .gitignore | 1 | ||||
-rw-r--r-- | Gemfile | 7 | ||||
-rw-r--r-- | actionpack/CHANGELOG.md | 14 | ||||
-rw-r--r-- | actionpack/lib/action_view/helpers/translation_helper.rb | 13 | ||||
-rw-r--r-- | actionpack/test/template/translation_helper_test.rb | 6 |
5 files changed, 32 insertions, 9 deletions
diff --git a/.gitignore b/.gitignore index aa14cee911..52a431867c 100644 --- a/.gitignore +++ b/.gitignore @@ -2,6 +2,7 @@ # Check out http://help.github.com/ignore-files/ for how to set that up. debug.log +.Gemfile /.bundle /.rbenv-version /.rvmrc @@ -36,13 +36,11 @@ gem "memcache-client", ">= 1.8.5" platforms :mri_18 do gem "system_timer" - gem "ruby-debug", ">= 0.10.3" unless ENV['TRAVIS'] gem "json" end -platforms :mri_19 do - gem "ruby-debug19", :require => "ruby-debug" unless ENV['TRAVIS'] || RUBY_VERSION >= "2.0" -end +# Add your own local bundler stuff +instance_eval File.read ".Gemfile" if File.exists? ".Gemfile" platforms :mri do group :test do @@ -69,7 +67,6 @@ platforms :ruby do end platforms :jruby do - gem "ruby-debug", ">= 0.10.3" gem "json" gem "activerecord-jdbcsqlite3-adapter", ">= 1.2.0" diff --git a/actionpack/CHANGELOG.md b/actionpack/CHANGELOG.md index 4c265c41d8..9d847c763b 100644 --- a/actionpack/CHANGELOG.md +++ b/actionpack/CHANGELOG.md @@ -64,6 +64,20 @@ ## Rails 3.1.2 (unreleased) ## +* Fix XSS security vulnerability in the `translate` helper method. When using interpolation + in combination with HTML-safe translations, the interpolated input would not get HTML + escaped. *GH 3664* + + Before: + + translate('foo_html', :something => '<script>') # => "...<script>..." + + After: + + translate('foo_html', :something => '<script>') # => "...<script>..." + + *Sergey Nartimov* + * Upgrade sprockets dependency to ~> 2.1.0 * Ensure that the format isn't applied twice to the cache key, else it becomes impossible diff --git a/actionpack/lib/action_view/helpers/translation_helper.rb b/actionpack/lib/action_view/helpers/translation_helper.rb index be64dc823e..42726f888c 100644 --- a/actionpack/lib/action_view/helpers/translation_helper.rb +++ b/actionpack/lib/action_view/helpers/translation_helper.rb @@ -45,11 +45,16 @@ module ActionView # you know what kind of output to expect when you call translate in a template. def translate(key, options = {}) options.merge!(:rescue_format => :html) unless options.key?(:rescue_format) - translation = I18n.translate(scope_key_by_partial(key), options) - if html_safe_translation_key?(key) && translation.respond_to?(:html_safe) - translation.html_safe + if html_safe_translation_key?(key) + html_safe_options = options.dup + options.except(*I18n::RESERVED_KEYS).each do |name, value| + html_safe_options[name] = ERB::Util.html_escape(value.to_s) + end + translation = I18n.translate(scope_key_by_partial(key), html_safe_options) + + translation.respond_to?(:html_safe) ? translation.html_safe : translation else - translation + I18n.translate(scope_key_by_partial(key), options) end end alias :t :translate diff --git a/actionpack/test/template/translation_helper_test.rb b/actionpack/test/template/translation_helper_test.rb index cd9f54e04c..cabb29cfad 100644 --- a/actionpack/test/template/translation_helper_test.rb +++ b/actionpack/test/template/translation_helper_test.rb @@ -17,6 +17,7 @@ class TranslationHelperTest < ActiveSupport::TestCase :hello => '<a>Hello World</a>', :html => '<a>Hello World</a>', :hello_html => '<a>Hello World</a>', + :interpolated_html => '<a>Hello %{word}</a>', :array_html => %w(foo bar), :array => %w(foo bar) } @@ -83,6 +84,11 @@ class TranslationHelperTest < ActiveSupport::TestCase assert translate(:'translations.hello_html').html_safe? end + def test_translate_escapes_interpolations_in_translations_with_a_html_suffix + assert_equal '<a>Hello <World></a>', translate(:'translations.interpolated_html', :word => '<World>') + assert_equal '<a>Hello <World></a>', translate(:'translations.interpolated_html', :word => stub(:to_s => "<World>")) + end + def test_translation_returning_an_array_ignores_html_suffix assert_equal ["foo", "bar"], translate(:'translations.array_html') end |