Script 'mail_helper' called by obssrc
Hello community,

here is the log from the commit of package rubygem-haml for openSUSE:Factory 
checked in at 2021-01-21 21:55:43
++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
Comparing /work/SRC/openSUSE:Factory/rubygem-haml (Old)
 and      /work/SRC/openSUSE:Factory/.rubygem-haml.new.28504 (New)
++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++

Package is "rubygem-haml"

Thu Jan 21 21:55:43 2021 rev:32 rq:865194 version:5.2.1

Changes:
--------
--- /work/SRC/openSUSE:Factory/rubygem-haml/rubygem-haml.changes        
2020-03-07 21:38:22.280277529 +0100
+++ /work/SRC/openSUSE:Factory/.rubygem-haml.new.28504/rubygem-haml.changes     
2021-01-21 21:55:44.181809851 +0100
@@ -1,0 +2,23 @@
+Wed Jan 20 12:46:37 UTC 2021 - Stephan Kulow <co...@suse.com>
+
+updated to version 5.2.1
+ see installed CHANGELOG.md
+
+  ## 5.2.1
+  
+  Released on November 30, 2020
+  ([diff](https://github.com/haml/haml/compare/v5.2.0...v5.2.1)).
+  
+  * Add in improved "multiline" support for attributes 
[#1043](https://github.com/haml/haml/issues/1043)
+  
+  ## 5.2
+  
+  Released on September 28, 2020
+  ([diff](https://github.com/haml/haml/compare/v5.1.2...v5.2.0)).
+  
+  * Fix crash in the attribute optimizer when `#inspect` is overridden in 
TrueClass / FalseClass [#972](https://github.com/haml/haml/issues/972)
+  * Do not HTML-escape templates that are declared to be plaintext 
[#1014](https://github.com/haml/haml/issues/1014) (Thanks 
[@cesarizu](https://github.com/cesarizu))
+  * Class names are no longer ordered alphabetically, and now follow a new 
specification as laid out in REFERENCE 
[#306](https://github.com/haml/haml/issues/306)
+  
+
+-------------------------------------------------------------------

Old:
----
  haml-5.1.2.gem

New:
----
  haml-5.2.1.gem

++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++

Other differences:
------------------
++++++ rubygem-haml.spec ++++++
--- /var/tmp/diff_new_pack.9JAjQi/_old  2021-01-21 21:55:44.805810286 +0100
+++ /var/tmp/diff_new_pack.9JAjQi/_new  2021-01-21 21:55:44.809810289 +0100
@@ -1,7 +1,7 @@
 #
 # spec file for package rubygem-haml
 #
-# Copyright (c) 2020 SUSE LLC
+# Copyright (c) 2021 SUSE LLC
 #
 # All modifications and additions to the file contributed by third parties
 # remain the property of their copyright owners, unless otherwise agreed
@@ -24,7 +24,7 @@
 #
 
 Name:           rubygem-haml
-Version:        5.1.2
+Version:        5.2.1
 Release:        0
 %define mod_name haml
 %define mod_full_name %{mod_name}-%{version}

++++++ haml-5.1.2.gem -> haml-5.2.1.gem ++++++
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/.gitignore new/.gitignore
--- old/.gitignore      2019-08-06 14:35:39.000000000 +0200
+++ new/.gitignore      2020-11-30 20:36:33.000000000 +0100
@@ -1,3 +1,4 @@
+/.idea
 /.yardoc
 /coverage
 /doc
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/.travis.yml new/.travis.yml
--- old/.travis.yml     2019-08-06 14:35:39.000000000 +0200
+++ new/.travis.yml     2020-11-30 20:36:33.000000000 +0100
@@ -1,18 +1,17 @@
 sudo: false
 dist: trusty
 language: ruby
-cache: bundler
+cache:
+  bundler: true
 rvm:
   - ruby-head
-  - 2.6.3
-  - 2.5.5
-  - 2.4.6
-  - 2.3.8
-  - 2.2.10
-  - 2.1.10
-  - 2.0.0
-  - jruby-9.2.7.0
-  - rbx-3
+  - 2.7
+  - 2.6
+  - 2.5
+  - jruby-9.2
+env:
+  - RUBYOPT="--enable-frozen-string-literal"
+  - RUBYOPT=""
 gemfile:
   - test/gemfiles/Gemfile.rails-6.0.x
   - test/gemfiles/Gemfile.rails-5.2.x
@@ -24,74 +23,89 @@
   - test/gemfiles/Gemfile.rails-4.0.x
 matrix:
   exclude:
-    - rvm: 2.0.0
-      gemfile: test/gemfiles/Gemfile.rails-6.0.x
-    - rvm: 2.1.10
-      gemfile: test/gemfiles/Gemfile.rails-6.0.x
-    - rvm: 2.2.10
-      gemfile: test/gemfiles/Gemfile.rails-6.0.x
-    - rvm: 2.3.8
-      gemfile: test/gemfiles/Gemfile.rails-6.0.x
-    - rvm: 2.4.6
-      gemfile: test/gemfiles/Gemfile.rails-6.0.x
-    - rvm: 2.0.0
-      gemfile: test/gemfiles/Gemfile.rails-5.2.x
-    - rvm: 2.1.10
-      gemfile: test/gemfiles/Gemfile.rails-5.2.x
-    - rvm: 2.0.0
-      gemfile: test/gemfiles/Gemfile.rails-5.1.x
-    - rvm: 2.1.10
-      gemfile: test/gemfiles/Gemfile.rails-5.1.x
-    - rvm: 2.0.0
-      gemfile: test/gemfiles/Gemfile.rails-5.0.x
-    - rvm: 2.0.0
-      gemfile: test/gemfiles/Gemfile.rails-5.0.x.erubi
-    - rvm: 2.1.10
-      gemfile: test/gemfiles/Gemfile.rails-5.0.x
-    - rvm: 2.1.10
-      gemfile: test/gemfiles/Gemfile.rails-5.0.x.erubi
-    - rvm: 2.4.6
+    - rvm: 2.5
       gemfile: test/gemfiles/Gemfile.rails-4.0.x
-    - rvm: 2.4.6
+    - rvm: 2.5
       gemfile: test/gemfiles/Gemfile.rails-4.1.x
-    - rvm: 2.4.6
+    - rvm: 2.5
       gemfile: test/gemfiles/Gemfile.rails-4.2.x
-    - rvm: 2.5.5
+    - rvm: 2.5
+      gemfile: test/gemfiles/Gemfile.rails-5.0.x
+      env: RUBYOPT="--enable-frozen-string-literal"
+    - rvm: 2.5
+      gemfile: test/gemfiles/Gemfile.rails-5.0.x.erubi
+      env: RUBYOPT="--enable-frozen-string-literal"
+    - rvm: 2.5
+      gemfile: test/gemfiles/Gemfile.rails-5.1.x
+      env: RUBYOPT="--enable-frozen-string-literal"
+    - rvm: 2.6
       gemfile: test/gemfiles/Gemfile.rails-4.0.x
-    - rvm: 2.5.5
+    - rvm: 2.6
       gemfile: test/gemfiles/Gemfile.rails-4.1.x
-    - rvm: 2.5.5
+    - rvm: 2.6
       gemfile: test/gemfiles/Gemfile.rails-4.2.x
-    - rvm: 2.6.3
+    - rvm: 2.6
+      gemfile: test/gemfiles/Gemfile.rails-5.0.x
+      env: RUBYOPT="--enable-frozen-string-literal"
+    - rvm: 2.6
+      gemfile: test/gemfiles/Gemfile.rails-5.0.x.erubi
+      env: RUBYOPT="--enable-frozen-string-literal"
+    - rvm: 2.6
+      gemfile: test/gemfiles/Gemfile.rails-5.1.x
+      env: RUBYOPT="--enable-frozen-string-literal"
+    - rvm: 2.7
       gemfile: test/gemfiles/Gemfile.rails-4.0.x
-    - rvm: 2.6.3
+    - rvm: 2.7
       gemfile: test/gemfiles/Gemfile.rails-4.1.x
-    - rvm: 2.6.3
+    - rvm: 2.7
       gemfile: test/gemfiles/Gemfile.rails-4.2.x
+    - rvm: 2.7
+      gemfile: test/gemfiles/Gemfile.rails-5.0.x
+      env: RUBYOPT="--enable-frozen-string-literal"
+    - rvm: 2.7
+      gemfile: test/gemfiles/Gemfile.rails-5.0.x.erubi
+      env: RUBYOPT="--enable-frozen-string-literal"
+    - rvm: 2.7
+      gemfile: test/gemfiles/Gemfile.rails-5.1.x
+      env: RUBYOPT="--enable-frozen-string-literal"
     - rvm: ruby-head
       gemfile: test/gemfiles/Gemfile.rails-4.0.x
     - rvm: ruby-head
       gemfile: test/gemfiles/Gemfile.rails-4.1.x
     - rvm: ruby-head
       gemfile: test/gemfiles/Gemfile.rails-4.2.x
+    - rvm: jruby-9.2
+      gemfile: test/gemfiles/Gemfile.rails-5.0.x
+      env: RUBYOPT="--enable-frozen-string-literal"
+    - rvm: jruby-9.2
+      gemfile: test/gemfiles/Gemfile.rails-5.0.x.erubi
+      env: RUBYOPT="--enable-frozen-string-literal"
+    - rvm: jruby-9.2
+      gemfile: test/gemfiles/Gemfile.rails-5.1.x
+      env: RUBYOPT="--enable-frozen-string-literal"
   include:
-    - rvm: 2.6.3
+    - rvm: 2.7
       gemfile: test/gemfiles/Gemfile.rails-edge
   allow_failures:
     - rvm: ruby-head
-    - rvm: rbx-3
     - gemfile: test/gemfiles/Gemfile.rails-edge
-    - rvm: jruby-9.2.7.0
+    - rvm: jruby-9.2
       gemfile: test/gemfiles/Gemfile.rails-4.2.x
-    - rvm: jruby-9.2.7.0
+    - rvm: jruby-9.2
       gemfile: test/gemfiles/Gemfile.rails-4.1.x
-    - rvm: jruby-9.2.7.0
+    - rvm: jruby-9.2
       gemfile: test/gemfiles/Gemfile.rails-4.0.x
-    - rvm: jruby-9.2.7.0
+    - rvm: jruby-9.2
       gemfile: test/gemfiles/Gemfile.rails-5.0.x.erubi
   fast_finish: true
 before_install:
-  - gem i rubygems-update -v '<3' && update_rubygems # 
https://github.com/travis-ci/travis-ci/issues/8974
-  - gem uninstall -v '>= 2' -i $(rvm gemdir)@global -ax bundler || true
-  - gem i bundler -v '<2'
+  # install older versions of rubygems and bundler only on Ruby < 2.7
+  - if [ `echo "${TRAVIS_RUBY_VERSION:0:3} < 2.7" | bc` == 1 ]; then gem i 
rubygems-update -v '<3' && update_rubygems; fi; # 
https://github.com/travis-ci/travis-ci/issues/8974
+  - if [ `echo "${TRAVIS_RUBY_VERSION:0:3} < 2.7" | bc` == 1 ]; then gem 
uninstall -v '>= 2' -i $(rvm gemdir)@global -ax bundler || true; fi;
+  - if [ `echo "${TRAVIS_RUBY_VERSION:0:3} < 2.7" | bc` == 1 ]; then gem i 
bundler -v '<2'; fi;
+  - curl -L 
https://codeclimate.com/downloads/test-reporter/test-reporter-latest-linux-amd64
 > ./cc-test-reporter
+  - chmod +x ./cc-test-reporter
+  - ./cc-test-reporter before-build
 script: "bundle exec rake submodules test"
+after_script:
+  - ./cc-test-reporter after-build --exit-code $TRAVIS_TEST_RESULT
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/CHANGELOG.md new/CHANGELOG.md
--- old/CHANGELOG.md    2019-08-06 14:35:39.000000000 +0200
+++ new/CHANGELOG.md    2020-11-30 20:36:33.000000000 +0100
@@ -1,5 +1,21 @@
 # Haml Changelog
 
+## 5.2.1
+
+Released on November 30, 2020
+([diff](https://github.com/haml/haml/compare/v5.2.0...v5.2.1)).
+
+* Add in improved "multiline" support for attributes 
[#1043](https://github.com/haml/haml/issues/1043)
+
+## 5.2
+
+Released on September 28, 2020
+([diff](https://github.com/haml/haml/compare/v5.1.2...v5.2.0)).
+
+* Fix crash in the attribute optimizer when `#inspect` is overridden in 
TrueClass / FalseClass [#972](https://github.com/haml/haml/issues/972)
+* Do not HTML-escape templates that are declared to be plaintext 
[#1014](https://github.com/haml/haml/issues/1014) (Thanks 
[@cesarizu](https://github.com/cesarizu))
+* Class names are no longer ordered alphabetically, and now follow a new 
specification as laid out in REFERENCE 
[#306](https://github.com/haml/haml/issues/306)
+
 ## 5.1.2
 
 Released on August 6, 2019
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/Gemfile new/Gemfile
--- old/Gemfile 2019-08-06 14:35:39.000000000 +0200
+++ new/Gemfile 2020-11-30 20:36:33.000000000 +0100
@@ -3,6 +3,7 @@
 
 gem "m"
 gem "pry"
+gem "simplecov"
 
 group :docs do
   gem "yard"
@@ -13,7 +14,3 @@
 platform :mri do
   gem "ruby-prof"
 end
-
-platform :mri_21 do
-  gem "simplecov"
-end
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/README.md new/README.md
--- old/README.md       2019-08-06 14:35:39.000000000 +0200
+++ new/README.md       2020-11-30 20:36:33.000000000 +0100
@@ -1,9 +1,8 @@
 # Haml
 
 [![Gem 
Version](https://badge.fury.io/rb/haml.svg)](http://rubygems.org/gems/haml)
-[![Build 
Status](https://travis-ci.org/haml/haml.svg?branch=master)](http://travis-ci.org/haml/haml)
+[![Build 
Status](https://travis-ci.org/haml/haml.svg?branch=main)](http://travis-ci.org/haml/haml)
 [![Code 
Climate](https://codeclimate.com/github/haml/haml/badges/gpa.svg)](https://codeclimate.com/github/haml/haml)
-[![Coverage 
Status](http://img.shields.io/coveralls/haml/haml.svg)](https://coveralls.io/r/haml/haml)
 [![Inline 
docs](http://inch-ci.org/github/haml/haml.png)](http://inch-ci.org/github/haml/haml)
 
 Haml is a templating engine for HTML. It's designed to make it both easier and
@@ -32,7 +31,7 @@
 haml --help
 ~~~
 
-To use Haml programatically, check out the [YARD 
documentation](http://haml.info/docs/yardoc/).
+To use Haml programmatically, check out the [YARD 
documentation](http://haml.info/docs/yardoc/).
 
 ## Using Haml with Rails
 
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/REFERENCE.md new/REFERENCE.md
--- old/REFERENCE.md    2019-08-06 14:35:39.000000000 +0200
+++ new/REFERENCE.md    2020-11-30 20:36:33.000000000 +0100
@@ -228,15 +228,19 @@
     <html xmlns='http://www.w3.org/1999/xhtml' xml:lang='en' lang='en'></html>
 
 Attribute hashes can also be stretched out over multiple lines to accommodate
-many attributes. However, newlines may only be placed immediately after commas.
-For example:
+many attributes.
 
-    %script{:type => "text/javascript",
-            :src  => "javascripts/script_#{2 + 7}"}
+    %script{
+      "type": text/javascript",
+      "src": javascripts/script_#{2 + 7}",
+      "data": {
+        "controller": "reporter",
+      },
+    }
 
 is compiled to:
 
-    <script src='javascripts/script_9' type='text/javascript'></script>
+    <script src='javascripts/script_9' type='text/javascript' 
data-controller='reporter'></script>
 
 #### `:class` and `:id` Attributes {#class-and-id-attributes}
 
@@ -517,6 +521,24 @@
       </div>
     </div>
 
+#### Class Name Merging and Ordering
+
+Class names are ordered in the following way:
+
+1) Tag identifiers in order (aka, ".alert.me" => "alert me")
+2) Classes appearing in HTML-style attributes
+3) Classes appearing in Hash-style attributes
+
+For instance, this is a complicated and unintuitive test case illustrating the 
ordering
+
+    .foo.moo{:class => ['bar', 'alpha']}(class='baz')
+
+The resulting HTML would be as follows:
+
+    <div class='foo moo baz bar alpha'></div>
+
+*Versions of Haml prior to 5.0 would alphabetically sort class names.*
+
 ### Empty (void) Tags: `/`
 
 The forward slash character, when placed at the end of a tag definition, causes
@@ -853,7 +875,7 @@
 
 ## Ruby Evaluation
 
-### Inserting Ruby: `=`
+### Inserting Ruby: `=` {#inserting_ruby}
 
 The equals character is followed by Ruby code. This code is evaluated and the
 output is inserted into the document. For example:
@@ -1323,7 +1345,7 @@
 So data structures and  functions that require lots of arguments
 can be wrapped over multiple lines,
 as long as each line but the last ends in a comma
-(see [Inserting Ruby](#inserting_ruby_)).
+(see [Inserting Ruby](#inserting_ruby)).
 
 ## Whitespace Preservation
 
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/Rakefile new/Rakefile
--- old/Rakefile        2019-08-06 14:35:39.000000000 +0200
+++ new/Rakefile        2020-11-30 20:36:33.000000000 +0100
@@ -14,7 +14,7 @@
 end
 Rake::TestTask.new do |t|
   t.libs << 'test'
-  t.test_files = Dir['test/*_test.rb'] + Dir['test/haml-spec/*_test.rb'] - 
isolated_test.file_list
+  t.test_files = Dir['test/*_test.rb'] + Dir['test/haml-spec/*_test.rb'] + 
Dir['test/cases/*_test.rb'] - isolated_test.file_list
   t.warning = true
   t.verbose = true
 end
@@ -26,13 +26,6 @@
   sh "ruby benchmark.rb #{ENV['TIMES']}"
 end
 
-task :set_coverage_env do
-  ENV["COVERAGE"] = "true"
-end
-
-desc "Run Simplecov"
-task :coverage => [:set_coverage_env, :test]
-
 task :submodules do
   if File.exist?(File.dirname(__FILE__) + "/.git")
     sh %{git submodule sync}
Binary files old/checksums.yaml.gz and new/checksums.yaml.gz differ
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/haml.gemspec new/haml.gemspec
--- old/haml.gemspec    2019-08-06 14:35:39.000000000 +0200
+++ new/haml.gemspec    2020-11-30 20:36:33.000000000 +0100
@@ -16,7 +16,7 @@
   spec.license     = "MIT"
   spec.metadata    = {
     "bug_tracker_uri"   => "https://github.com/haml/haml/issues";,
-    "changelog_uri"     => 
"https://github.com/haml/haml/blob/master/CHANGELOG.md";,
+    "changelog_uri"     => 
"https://github.com/haml/haml/blob/main/CHANGELOG.md";,
     "documentation_uri" => "http://haml.info/docs.html";,
     "homepage_uri"      => "http://haml.info";,
     "mailing_list_uri"  => 
"https://groups.google.com/forum/?fromgroups#!forum/haml";,
@@ -32,6 +32,7 @@
   spec.add_development_dependency 'rbench'
   spec.add_development_dependency 'minitest', '>= 4.0'
   spec.add_development_dependency 'nokogiri'
+  spec.add_development_dependency 'simplecov'
 
   spec.description = <<-END
 Haml (HTML Abstraction Markup Language) is a layer on top of HTML or XML that's
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/lib/haml/attribute_builder.rb 
new/lib/haml/attribute_builder.rb
--- old/lib/haml/attribute_builder.rb   2019-08-06 14:35:39.000000000 +0200
+++ new/lib/haml/attribute_builder.rb   2020-11-30 20:36:33.000000000 +0100
@@ -36,9 +36,9 @@
 
           value =
             if escape_attrs == :once
-              Haml::Helpers.escape_once(value.to_s)
+              Haml::Helpers.escape_once_without_haml_xss(value.to_s)
             elsif escape_attrs
-              Haml::Helpers.html_escape(value.to_s)
+              Haml::Helpers.html_escape_without_haml_xss(value.to_s)
             else
               value.to_s
             end
@@ -126,7 +126,7 @@
         elsif key == 'class'
           merged_class = filter_and_join(from, ' ')
           if to && merged_class
-            merged_class = (merged_class.split(' ') | to.split(' 
')).sort.join(' ')
+            merged_class = (to.split(' ') | merged_class.split(' ')).join(' ')
           elsif to || merged_class
             merged_class ||= to
           end
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/lib/haml/attribute_compiler.rb 
new/lib/haml/attribute_compiler.rb
--- old/lib/haml/attribute_compiler.rb  2019-08-06 14:35:39.000000000 +0200
+++ new/lib/haml/attribute_compiler.rb  2020-11-30 20:36:33.000000000 +0100
@@ -7,27 +7,7 @@
     # @param type [Symbol] :static or :dynamic
     # @param key [String]
     # @param value [String] Actual string value for :static type, value's Ruby 
literal for :dynamic type.
-    AttributeValue = Struct.new(:type, :key, :value) do
-      # @return [String] A Ruby literal of value.
-      def to_literal
-        case type
-        when :static
-          Haml::Util.inspect_obj(value)
-        when :dynamic
-          value
-        end
-      end
-    end
-
-    # Returns a script to render attributes on runtime.
-    #
-    # @param attributes [Hash]
-    # @param object_ref [String,:nil]
-    # @param dynamic_attributes [DynamicAttributes]
-    # @return [String] Attributes rendering code
-    def self.runtime_build(attributes, object_ref, dynamic_attributes)
-      "_hamlout.attributes(#{Haml::Util.inspect_obj(attributes)}, 
#{object_ref},#{dynamic_attributes.to_literal})"
-    end
+    AttributeValue = Struct.new(:type, :key, :value)
 
     # @param options [Haml::Options]
     def initialize(options)
@@ -41,16 +21,16 @@
     #
     # @param attributes [Hash]
     # @param object_ref [String,:nil]
-    # @param dynamic_attributes [DynamicAttributes]
+    # @param dynamic_attributes [Haml::Parser::DynamicAttributes]
     # @return [Array] Temple expression
     def compile(attributes, object_ref, dynamic_attributes)
       if object_ref != :nil || !AttributeParser.available?
-        return [:dynamic, AttributeCompiler.runtime_build(attributes, 
object_ref, dynamic_attributes)]
+        return [:dynamic, compile_runtime_build(attributes, object_ref, 
dynamic_attributes)]
       end
 
       parsed_hashes = [dynamic_attributes.new, 
dynamic_attributes.old].compact.map do |attribute_hash|
         unless (hash = AttributeParser.parse(attribute_hash))
-          return [:dynamic, AttributeCompiler.runtime_build(attributes, 
object_ref, dynamic_attributes)]
+          return [:dynamic, compile_runtime_build(attributes, object_ref, 
dynamic_attributes)]
         end
         hash
       end
@@ -64,6 +44,16 @@
 
     private
 
+    # Returns a script to render attributes on runtime.
+    #
+    # @param attributes [Hash]
+    # @param object_ref [String,:nil]
+    # @param dynamic_attributes [Haml::Parser::DynamicAttributes]
+    # @return [String] Attributes rendering code
+    def compile_runtime_build(attributes, object_ref, dynamic_attributes)
+      "_hamlout.attributes(#{to_literal(attributes)}, #{object_ref}, 
#{dynamic_attributes.to_literal})"
+    end
+
     # Build array of grouped values whose sort order may go back and forth, 
which is also sorted with key name.
     # This method needs to group values with the same start because it can be 
changed in `Haml::AttributeBuidler#build_data_keys`.
     # @param values [Array<Haml::AttributeCompiler::AttributeValue>]
@@ -130,7 +120,7 @@
 
       arguments = [@is_html, @attr_wrapper, @escape_attrs, 
@hyphenate_data_attrs]
       code = "::Haml::AttributeBuilder.build_attributes"\
-        "(#{arguments.map { |a| Haml::Util.inspect_obj(a) }.join(', ')}, { 
#{hash_content} })"
+        "(#{arguments.map(&method(:to_literal)).join(', ')}, { #{hash_content} 
})"
       [:static, eval(code).to_s]
     end
 
@@ -139,16 +129,16 @@
     # @return [String]
     def merged_value(key, values)
       if values.size == 1
-        values.first.to_literal
+        attr_literal(values.first)
       else
-        "::Haml::AttributeBuilder.merge_values(#{frozen_string(key)}, 
#{values.map(&:to_literal).join(', ')})"
+        "::Haml::AttributeBuilder.merge_values(#{frozen_string(key)}, 
#{values.map(&method(:attr_literal)).join(', ')})"
       end
     end
 
     # @param str [String]
     # @return [String]
     def frozen_string(str)
-      "#{Haml::Util.inspect_obj(str)}.freeze"
+      "#{to_literal(str)}.freeze"
     end
 
     # Compiles attribute values for one key to Temple expression that 
generates ` key='value'`.
@@ -157,7 +147,7 @@
     # @param values [Array<AttributeValue>]
     # @return [Array] Temple expression
     def compile_attribute(key, values)
-      if values.all? { |v| Temple::StaticAnalyzer.static?(v.to_literal) }
+      if values.all? { |v| Temple::StaticAnalyzer.static?(attr_literal(v)) }
         return static_build(values)
       end
 
@@ -181,7 +171,7 @@
         ['false, nil', [:multi]],
         [:else, [:multi,
                  [:static, " #{id_or_class}=#{@attr_wrapper}"],
-                 [:escape, @escape_attrs, [:dynamic, var]],
+                 [:escape, Escapable::EscapeSafeBuffer.new(@escape_attrs), 
[:dynamic, var]],
                  [:static, @attr_wrapper]],
         ]
        ],
@@ -201,7 +191,7 @@
         ['false, nil', [:multi]],
         [:else, [:multi,
                  [:static, " #{key}=#{@attr_wrapper}"],
-                 [:escape, @escape_attrs, [:dynamic, var]],
+                 [:escape, Escapable::EscapeSafeBuffer.new(@escape_attrs), 
[:dynamic, var]],
                  [:static, @attr_wrapper]],
         ]
        ],
@@ -220,5 +210,26 @@
       @unique_name ||= 0
       "_haml_attribute_compiler#{@unique_name += 1}"
     end
+
+    # @param [Haml::AttributeCompiler::AttributeValue] attr
+    def attr_literal(attr)
+      case attr.type
+      when :static
+        to_literal(attr.value)
+      when :dynamic
+        attr.value
+      end
+    end
+
+    # For haml/haml#972
+    # @param [Object] value
+    def to_literal(value)
+      case value
+      when true, false
+        value.to_s
+      else
+        Haml::Util.inspect_obj(value)
+      end
+    end
   end
 end
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/lib/haml/escapable.rb new/lib/haml/escapable.rb
--- old/lib/haml/escapable.rb   2019-08-06 14:35:39.000000000 +0200
+++ new/lib/haml/escapable.rb   2020-11-30 20:36:33.000000000 +0100
@@ -4,30 +4,31 @@
   # Like Temple::Filters::Escapable, but with support for escaping by
   # Haml::Herlpers.html_escape and Haml::Herlpers.escape_once.
   class Escapable < Temple::Filter
+    # Special value of `flag` to ignore html_safe?
+    EscapeSafeBuffer = Struct.new(:value)
+
     def initialize(*)
       super
-      @escape_code = "::Haml::Helpers.html_escape((%s))"
-      @escaper = eval("proc {|v| #{@escape_code % 'v'} }")
-      @once_escape_code = "::Haml::Helpers.escape_once((%s))"
-      @once_escaper = eval("proc {|v| #{@once_escape_code % 'v'} }")
       @escape = false
+      @escape_safe_buffer = false
     end
 
     def on_escape(flag, exp)
-      old = @escape
-      @escape = flag
+      old_escape, old_escape_safe_buffer = @escape, @escape_safe_buffer
+      @escape_safe_buffer = flag.is_a?(EscapeSafeBuffer)
+      @escape = @escape_safe_buffer ? flag.value : flag
       compile(exp)
     ensure
-      @escape = old
+      @escape, @escape_safe_buffer = old_escape, old_escape_safe_buffer
     end
 
     # The same as Haml::AttributeBuilder.build_attributes
     def on_static(value)
       [:static,
        if @escape == :once
-         @once_escaper[value]
+         escape_once(value)
        elsif @escape
-         @escaper[value]
+         escape(value)
        else
          value
        end
@@ -38,13 +39,39 @@
     def on_dynamic(value)
       [:dynamic,
        if @escape == :once
-         @once_escape_code % value
+         escape_once_code(value)
        elsif @escape
-         @escape_code % value
+         escape_code(value)
        else
          "(#{value}).to_s"
        end
       ]
     end
+
+    private
+
+    def escape_once(value)
+      if @escape_safe_buffer
+        ::Haml::Helpers.escape_once_without_haml_xss(value)
+      else
+        ::Haml::Helpers.escape_once(value)
+      end
+    end
+
+    def escape(value)
+      if @escape_safe_buffer
+        ::Haml::Helpers.html_escape_without_haml_xss(value)
+      else
+        ::Haml::Helpers.html_escape(value)
+      end
+    end
+
+    def escape_once_code(value)
+      "::Haml::Helpers.escape_once#{('_without_haml_xss' if 
@escape_safe_buffer)}((#{value}))"
+    end
+
+    def escape_code(value)
+      "::Haml::Helpers.html_escape#{('_without_haml_xss' if 
@escape_safe_buffer)}((#{value}))"
+    end
   end
 end
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/lib/haml/helpers/xss_mods.rb 
new/lib/haml/helpers/xss_mods.rb
--- old/lib/haml/helpers/xss_mods.rb    2019-08-06 14:35:39.000000000 +0200
+++ new/lib/haml/helpers/xss_mods.rb    2020-11-30 20:36:33.000000000 +0100
@@ -8,12 +8,15 @@
     # to work with Rails' XSS protection methods.
     module XssMods
       def self.included(base)
-        %w[html_escape find_and_preserve preserve list_of surround
-           precede succeed capture_haml haml_concat haml_internal_concat 
haml_indent
-           escape_once].each do |name|
+        %w[find_and_preserve preserve list_of surround
+           precede succeed capture_haml haml_concat haml_internal_concat 
haml_indent].each do |name|
           base.send(:alias_method, "#{name}_without_haml_xss", name)
           base.send(:alias_method, name, "#{name}_with_haml_xss")
         end
+        # Those two always have _without_haml_xss
+        %w[html_escape escape_once].each do |name|
+          base.send(:alias_method, name, "#{name}_with_haml_xss")
+        end
       end
 
       # Don't escape text that's already safe,
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/lib/haml/helpers.rb new/lib/haml/helpers.rb
--- old/lib/haml/helpers.rb     2019-08-06 14:35:39.000000000 +0200
+++ new/lib/haml/helpers.rb     2020-11-30 20:36:33.000000000 +0100
@@ -607,9 +607,12 @@
     # @param text [String] The string to sanitize
     # @return [String] The sanitized string
     def html_escape(text)
-      ERB::Util.html_escape(text)
+      CGI.escapeHTML(text.to_s)
     end
 
+    # Always escape text regardless of html_safe?
+    alias_method :html_escape_without_haml_xss, :html_escape
+
     HTML_ESCAPE_ONCE_REGEX = 
/['"><]|&(?!(?:[a-zA-Z]+|#(?:\d+|[xX][0-9a-fA-F]+));)/
 
     # Escapes HTML entities in `text`, but without escaping an ampersand
@@ -622,6 +625,9 @@
       text.gsub(HTML_ESCAPE_ONCE_REGEX, HTML_ESCAPE)
     end
 
+    # Always escape text once regardless of html_safe?
+    alias_method :escape_once_without_haml_xss, :escape_once
+
     # Returns whether or not the current template is a Haml template.
     #
     # This function, unlike other {Haml::Helpers} functions,
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/lib/haml/parser.rb new/lib/haml/parser.rb
--- old/lib/haml/parser.rb      2019-08-06 14:35:39.000000000 +0200
+++ new/lib/haml/parser.rb      2020-11-30 20:36:33.000000000 +0100
@@ -1,5 +1,6 @@
 # frozen_string_literal: true
 
+require 'ripper'
 require 'strscan'
 
 module Haml
@@ -90,6 +91,9 @@
     ID_KEY    = 'id'.freeze
     CLASS_KEY = 'class'.freeze
 
+    # Used for scanning old attributes, substituting the first '{'
+    METHOD_CALL_PREFIX = 'a('
+
     def initialize(options)
       @options = Options.wrap(options)
       # Record the indent levels of "if" statements to validate the subsequent
@@ -307,7 +311,7 @@
         return ParseNode.new(:plain, line.index + 1, :text => line.text)
       end
 
-      escape_html = @options.escape_html if escape_html.nil?
+      escape_html = @options.escape_html && @options.mime_type != 'text/plain' 
if escape_html.nil?
       line.text = unescape_interpolation(line.text, escape_html)
       script(line, false)
     end
@@ -651,13 +655,18 @@
     # @return [String] rest
     # @return [Integer] last_line
     def parse_old_attributes(text)
-      text = text.dup
       last_line = @line.index + 1
 
       begin
-        attributes_hash, rest = balance(text, ?{, ?})
+        # Old attributes often look like a valid Hash literal, but it 
sometimes allow code like
+        # `{ hash, foo: bar }`, which is compiled to `_hamlout.attributes({}, 
nil, hash, foo: bar)`.
+        #
+        # To scan such code correctly, this scans `a( hash, foo: bar }` 
instead, stops when there is
+        # 1 more :on_embexpr_end (the last '}') than :on_embexpr_beg, and 
resurrects '{' afterwards.
+        balanced, rest = balance_tokens(text.sub(?{, METHOD_CALL_PREFIX), 
:on_embexpr_beg, :on_embexpr_end, count: 1)
+        attributes_hash = balanced.sub(METHOD_CALL_PREFIX, ?{)
       rescue SyntaxError => e
-        if text.strip[-1] == ?, && e.message == 
Error.message(:unbalanced_brackets)
+        if e.message == Error.message(:unbalanced_brackets) && 
!@template.empty?
           text << "\n#{@next_line.text}"
           last_line += 1
           next_line
@@ -811,6 +820,25 @@
       Haml::Util.balance(*args) or 
raise(SyntaxError.new(Error.message(:unbalanced_brackets)))
     end
 
+    # Unlike #balance, this balances Ripper tokens to balance something like 
`{ a: "}" }` correctly.
+    def balance_tokens(buf, start, finish, count: 0)
+      text = ''.dup
+      Ripper.lex(buf).each do |_, token, str|
+        text << str
+        case token
+        when start
+          count += 1
+        when finish
+          count -= 1
+        end
+
+        if count == 0
+          return text, buf.sub(text, '')
+        end
+      end
+      raise SyntaxError.new(Error.message(:unbalanced_brackets))
+    end
+
     def block_opened?
       @next_line.tabs > @line.tabs
     end
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/lib/haml/util.rb new/lib/haml/util.rb
--- old/lib/haml/util.rb        2019-08-06 14:35:39.000000000 +0200
+++ new/lib/haml/util.rb        2020-11-30 20:36:33.000000000 +0100
@@ -213,7 +213,7 @@
             scan.scan(/\w+/)
           end
           content = eval("\"#{interpolated}\"")
-          content.prepend(char) if char == '@' || char == '$'
+          content = "#{char}#{content}" if char == '@' || char == '$'
           content = "Haml::Helpers.html_escape((#{content}))" if escape_html
 
           res << "\#{#{content}}"
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/lib/haml/version.rb new/lib/haml/version.rb
--- old/lib/haml/version.rb     2019-08-06 14:35:39.000000000 +0200
+++ new/lib/haml/version.rb     2020-11-30 20:36:33.000000000 +0100
@@ -1,5 +1,5 @@
 # frozen_string_literal: true
 
 module Haml
-  VERSION = "5.1.2"
+  VERSION = "5.2.1"
 end
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/metadata new/metadata
--- old/metadata        2019-08-06 14:35:39.000000000 +0200
+++ new/metadata        2020-11-30 20:36:33.000000000 +0100
@@ -1,17 +1,17 @@
 --- !ruby/object:Gem::Specification
 name: haml
 version: !ruby/object:Gem::Version
-  version: 5.1.2
+  version: 5.2.1
 platform: ruby
 authors:
 - Natalie Weizenbaum
 - Hampton Catlin
 - Norman Clarke
 - Akira Matsuda
-autorequire: 
+autorequire:
 bindir: bin
 cert_chain: []
-date: 2019-08-06 00:00:00.000000000 Z
+date: 2020-11-30 00:00:00.000000000 Z
 dependencies:
 - !ruby/object:Gem::Dependency
   name: temple
@@ -97,6 +97,20 @@
     - - ">="
       - !ruby/object:Gem::Version
         version: '0'
+- !ruby/object:Gem::Dependency
+  name: simplecov
+  requirement: !ruby/object:Gem::Requirement
+    requirements:
+    - - ">="
+      - !ruby/object:Gem::Version
+        version: '0'
+  type: :development
+  prerelease: false
+  version_requirements: !ruby/object:Gem::Requirement
+    requirements:
+    - - ">="
+      - !ruby/object:Gem::Version
+        version: '0'
 description: |
   Haml (HTML Abstraction Markup Language) is a layer on top of HTML or XML 
that's
   designed to express the structure of documents in a non-repetitive, elegant, 
and
@@ -165,12 +179,12 @@
 - MIT
 metadata:
   bug_tracker_uri: https://github.com/haml/haml/issues
-  changelog_uri: https://github.com/haml/haml/blob/master/CHANGELOG.md
+  changelog_uri: https://github.com/haml/haml/blob/main/CHANGELOG.md
   documentation_uri: http://haml.info/docs.html
   homepage_uri: http://haml.info
   mailing_list_uri: https://groups.google.com/forum/?fromgroups#!forum/haml
   source_code_uri: https://github.com/haml/haml
-post_install_message: 
+post_install_message:
 rdoc_options: []
 require_paths:
 - lib
@@ -185,8 +199,8 @@
     - !ruby/object:Gem::Version
       version: '0'
 requirements: []
-rubygems_version: 3.0.3
-signing_key: 
+rubygems_version: 3.1.4
+signing_key:
 specification_version: 4
 summary: An elegant, structured (X)HTML/XML templating engine.
 test_files: []

Reply via email to