diff --git a/activesupport/CHANGELOG.md b/activesupport/CHANGELOG.md index 2ab6721fa2..2a345193af 100644 --- a/activesupport/CHANGELOG.md +++ b/activesupport/CHANGELOG.md @@ -1,3 +1,8 @@ +* Invoking `Object#with_options` without a `&block` argument returns the + `ActiveSupport::OptionMerger` instance. + + *Sean Doyle* + * `Rails.application.executor` hooks are now called around every tests. This helps to better simulate request or job local state being reset around tests and prevent state diff --git a/activesupport/lib/active_support/core_ext/object/with_options.rb b/activesupport/lib/active_support/core_ext/object/with_options.rb index 1d46add6e0..a587ef6cc5 100644 --- a/activesupport/lib/active_support/core_ext/object/with_options.rb +++ b/activesupport/lib/active_support/core_ext/object/with_options.rb @@ -75,8 +75,27 @@ class Object # end # end # + # When the block argument is omitted, the decorated Object instance is returned: + # + # module MyStyledHelpers + # def styled + # with_options style: "color: red;" + # end + # end + # + # # styled.link_to "I'm red", "/" + # # #=> I'm red + # + # # styled.button_tag "I'm red too!" + # # #=> + # def with_options(options, &block) option_merger = ActiveSupport::OptionMerger.new(self, options) - block.arity.zero? ? option_merger.instance_eval(&block) : block.call(option_merger) + + if block.nil? + option_merger + else + block.arity.zero? ? option_merger.instance_eval(&block) : block.call(option_merger) + end end end diff --git a/activesupport/lib/active_support/option_merger.rb b/activesupport/lib/active_support/option_merger.rb index 696bbedd41..4c7720af82 100644 --- a/activesupport/lib/active_support/option_merger.rb +++ b/activesupport/lib/active_support/option_merger.rb @@ -30,5 +30,9 @@ module ActiveSupport @context.__send__(method, *arguments, &block) end end + + def respond_to_missing?(*arguments) + @context.respond_to?(*arguments) + end end end diff --git a/activesupport/test/option_merger_test.rb b/activesupport/test/option_merger_test.rb index d77e05c990..b2126ba0b2 100644 --- a/activesupport/test/option_merger_test.rb +++ b/activesupport/test/option_merger_test.rb @@ -105,6 +105,14 @@ class OptionMergerTest < ActiveSupport::TestCase assert_equal expected, @options end + def test_with_options_no_block + local_options = { "cool" => true } + scope = with_options(@options) + + assert_equal local_options, method_with_options(local_options) + assert_equal @options.merge(local_options), scope.method_with_options(local_options) + end + private def method_with_options(options = {}) options