<?xml version="1.0" encoding="UTF-8"?>
<commit>
  <added type="array">
    <added>
      <filename>activesupport/lib/active_support/core_ext/hash/deep_merge.rb</filename>
    </added>
  </added>
  <modified type="array">
    <modified>
      <diff>@@ -1,10 +1,11 @@
-%w(keys indifferent_access reverse_merge conversions diff slice except).each do |ext|
+%w(keys indifferent_access deep_merge reverse_merge conversions diff slice except).each do |ext|
   require &quot;active_support/core_ext/hash/#{ext}&quot;
 end
 
 class Hash #:nodoc:
   include ActiveSupport::CoreExtensions::Hash::Keys
   include ActiveSupport::CoreExtensions::Hash::IndifferentAccess
+  include ActiveSupport::CoreExtensions::Hash::DeepMerge
   include ActiveSupport::CoreExtensions::Hash::ReverseMerge
   include ActiveSupport::CoreExtensions::Hash::Conversions
   include ActiveSupport::CoreExtensions::Hash::Diff</diff>
      <filename>activesupport/lib/active_support/core_ext/hash.rb</filename>
    </modified>
    <modified>
      <diff>@@ -10,16 +10,8 @@ module ActiveSupport
 
     private
       def method_missing(method, *arguments, &amp;block)
-        merge_argument_options! arguments
+        arguments &lt;&lt; (arguments.last.respond_to?(:to_hash) ? @options.deep_merge(arguments.pop) : @options.dup)
         @context.send!(method, *arguments, &amp;block)
       end
-
-      def merge_argument_options!(arguments)
-        arguments &lt;&lt; if arguments.last.respond_to? :to_hash
-          @options.merge(arguments.pop)
-        else
-          @options.dup
-        end
-      end
   end
 end</diff>
      <filename>activesupport/lib/active_support/option_merger.rb</filename>
    </modified>
    <modified>
      <diff>@@ -245,6 +245,16 @@ class HashExtTest &lt; Test::Unit::TestCase
     assert(!indiff.keys.any? {|k| k.kind_of? String}, &quot;A key was converted to a string!&quot;)
   end
 
+  def test_deep_merge
+    hash_1 = { :a =&gt; &quot;a&quot;, :b =&gt; &quot;b&quot;, :c =&gt; { :c1 =&gt; &quot;c1&quot;, :c2 =&gt; &quot;c2&quot;, :c3 =&gt; { :d1 =&gt; &quot;d1&quot; } } }
+    hash_2 = { :a =&gt; 1, :c =&gt; { :c1 =&gt; 2, :c3 =&gt; { :d2 =&gt; &quot;d2&quot; } } }
+    expected = { :a =&gt; 1, :b =&gt; &quot;b&quot;, :c =&gt; { :c1 =&gt; 2, :c2 =&gt; &quot;c2&quot;, :c3 =&gt; { :d1 =&gt; &quot;d1&quot;, :d2 =&gt; &quot;d2&quot; } } }
+    assert_equal expected, hash_1.deep_merge(hash_2)
+
+    hash_1.deep_merge!(hash_2)
+    assert_equal expected, hash_1
+  end
+
   def test_reverse_merge
     defaults = { :a =&gt; &quot;x&quot;, :b =&gt; &quot;y&quot;, :c =&gt; 10 }.freeze
     options  = { :a =&gt; 1, :b =&gt; 2 }</diff>
      <filename>activesupport/test/core_ext/hash_ext_test.rb</filename>
    </modified>
    <modified>
      <diff>@@ -38,6 +38,33 @@ class OptionMergerTest &lt; Test::Unit::TestCase
     end
   end
 
+  def test_nested_method_with_options_containing_hashes_merge
+    with_options :conditions =&gt; { :method =&gt; :get } do |outer|
+      outer.with_options :conditions =&gt; { :domain =&gt; &quot;www&quot; } do |inner|
+        expected = { :conditions =&gt; { :method =&gt; :get, :domain =&gt; &quot;www&quot; } }
+        assert_equal expected, inner.method_with_options
+      end
+    end
+  end
+
+  def test_nested_method_with_options_containing_hashes_overwrite
+    with_options :conditions =&gt; { :method =&gt; :get, :domain =&gt; &quot;www&quot; } do |outer|
+      outer.with_options :conditions =&gt; { :method =&gt; :post } do |inner|
+        expected = { :conditions =&gt; { :method =&gt; :post, :domain =&gt; &quot;www&quot; } }
+        assert_equal expected, inner.method_with_options
+      end
+    end
+  end
+
+  def test_nested_method_with_options_containing_hashes_going_deep
+    with_options :html =&gt; { :class =&gt; &quot;foo&quot;, :style =&gt; { :margin =&gt; 0, :display =&gt; &quot;block&quot; } } do |outer|
+      outer.with_options :html =&gt; { :title =&gt; &quot;bar&quot;, :style =&gt; { :margin =&gt; &quot;1em&quot;, :color =&gt; &quot;#fff&quot; } } do |inner|
+        expected = { :html =&gt; { :class =&gt; &quot;foo&quot;, :title =&gt; &quot;bar&quot;, :style =&gt; { :margin =&gt; &quot;1em&quot;, :display =&gt; &quot;block&quot;, :color =&gt; &quot;#fff&quot; } } }
+        assert_equal expected, inner.method_with_options
+      end
+    end
+  end
+
   # Needed when counting objects with the ObjectSpace
   def test_option_merger_class_method
     assert_equal ActiveSupport::OptionMerger, ActiveSupport::OptionMerger.new('', '').class</diff>
      <filename>activesupport/test/option_merger_test.rb</filename>
    </modified>
  </modified>
  <removed type="array"/>
  <parents type="array">
    <parent>
      <id>cd6301557005617583e3f9ca5fb56297adcce7cc</id>
    </parent>
  </parents>
  <author>
    <name>Lawrence Pit</name>
    <email>lawrence.pit@gmail.com</email>
  </author>
  <url>http://github.com/rails/rails/commit/40dbebba28bfa1c55737da7354542c3bdca4e1a1</url>
  <id>40dbebba28bfa1c55737da7354542c3bdca4e1a1</id>
  <committed-date>2008-07-16T17:59:08-07:00</committed-date>
  <authored-date>2008-07-13T18:53:41-07:00</authored-date>
  <message>Allow deep merging of hash values for nested with_options. [#490 state:resolved]

Signed-off-by: Pratik Naik &lt;pratiknaik@gmail.com&gt;</message>
  <tree>f21c9a31379dae25b5cedae5ea00053a272d9408</tree>
  <committer>
    <name>Pratik Naik</name>
    <email>pratiknaik@gmail.com</email>
  </committer>
</commit>
