Skip to content
This repository was archived by the owner on Nov 30, 2024. It is now read-only.

Commit 93b16b2

Browse files
committed
Only apply modules to highest level matching group
For the behaviour when apploying helper modules to existing example groups to be fully consistent with the behaviour for new groups, we shouldn't apply the module if any of the example group's parent groups already have the module applied. Also refactor how we add hooks to existing groups to use the same code.
1 parent 6dfaa30 commit 93b16b2

File tree

3 files changed

+24
-32
lines changed

3 files changed

+24
-32
lines changed

Gemfile

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -40,7 +40,7 @@ gem 'simplecov', '~> 0.8'
4040
unless RUBY_VERSION == "1.9.2"
4141
gem "rubocop",
4242
"~> 0.32.1",
43-
:platform => [:ruby_19, :ruby_20, :ruby_21, :ruby_22]
43+
:platform => [:ruby_19, :ruby_20, :ruby_21, :ruby_22, :ruby_23]
4444
end
4545

4646
gem 'test-unit', '~> 3.0' if RUBY_VERSION.to_f >= 2.2

lib/rspec/core/configuration.rb

Lines changed: 21 additions & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -1749,7 +1749,8 @@ def before(scope=nil, *meta, &block)
17491749
handle_suite_hook(scope, meta) do
17501750
@before_suite_hooks << Hooks::BeforeHook.new(block, {})
17511751
end || begin
1752-
add_hook_to_existing_groups(:append, :before, scope, *meta, &block)
1752+
metadata = Metadata.build_hash_from(meta.dup)
1753+
on_existing_matching_groups(metadata, scope) { |g| g.before(scope, *meta, &block) }
17531754
super(scope, *meta, &block)
17541755
end
17551756
end
@@ -1772,7 +1773,8 @@ def prepend_before(scope=nil, *meta, &block)
17721773
handle_suite_hook(scope, meta) do
17731774
@before_suite_hooks.unshift Hooks::BeforeHook.new(block, {})
17741775
end || begin
1775-
add_hook_to_existing_groups(:prepend, :before, scope, *meta, &block)
1776+
metadata = Metadata.build_hash_from(meta.dup)
1777+
on_existing_matching_groups(metadata, scope) { |g| g.prepend_before(scope, *meta, &block) }
17761778
super(scope, *meta, &block)
17771779
end
17781780
end
@@ -1790,7 +1792,8 @@ def after(scope=nil, *meta, &block)
17901792
handle_suite_hook(scope, meta) do
17911793
@after_suite_hooks.unshift Hooks::AfterHook.new(block, {})
17921794
end || begin
1793-
add_hook_to_existing_groups(:prepend, :after, scope, *meta, &block)
1795+
metadata = Metadata.build_hash_from(meta.dup)
1796+
on_existing_matching_groups(metadata, scope) { |g| g.after(scope, *meta, &block) }
17941797
super(scope, *meta, &block)
17951798
end
17961799
end
@@ -1813,7 +1816,8 @@ def append_after(scope=nil, *meta, &block)
18131816
handle_suite_hook(scope, meta) do
18141817
@after_suite_hooks << Hooks::AfterHook.new(block, {})
18151818
end || begin
1816-
add_hook_to_existing_groups(:append, :after, scope, *meta, &block)
1819+
metadata = Metadata.build_hash_from(meta.dup)
1820+
on_existing_matching_groups(metadata, scope) { |g| g.append_after(scope, *meta, &block) }
18171821
super(scope, *meta, &block)
18181822
end
18191823
end
@@ -1822,7 +1826,8 @@ def append_after(scope=nil, *meta, &block)
18221826
#
18231827
# See {Hooks#around} for full `around` hook docs.
18241828
def around(scope=nil, *meta, &block)
1825-
add_hook_to_existing_groups(:prepend, :around, scope, *meta, &block)
1829+
metadata = Metadata.build_hash_from(meta.dup)
1830+
on_existing_matching_groups(metadata, scope) { |g| g.around(scope, *meta, &block) }
18261831
super(scope, *meta, &block)
18271832
end
18281833

@@ -2026,15 +2031,18 @@ def configure_group_with(group, module_list, application_method)
20262031
end
20272032
end
20282033

2029-
def on_existing_matching_groups(meta)
2030-
world.all_example_groups.each do |group|
2031-
yield group if meta.empty? || MetadataFilter.apply?(:any?, meta, group.metadata)
2032-
end
2033-
end
2034+
def on_existing_matching_groups(meta, scope=:ignore)
2035+
groups = world.example_groups.dup
2036+
2037+
until groups.empty?
2038+
group = groups.shift
20342039

2035-
def add_hook_to_existing_groups(prepend_or_append, position, *meta, &block)
2036-
world.example_groups.each do |group|
2037-
group.hooks.register_global_hook(prepend_or_append, position, *meta, &block)
2040+
if scope == :example || scope == :each || scope.nil? ||
2041+
meta.empty? || MetadataFilter.apply?(:any?, meta, group.metadata)
2042+
yield group
2043+
else
2044+
groups.concat(group.children)
2045+
end
20382046
end
20392047
end
20402048

lib/rspec/core/hooks.rb

Lines changed: 2 additions & 18 deletions
Original file line numberDiff line numberDiff line change
@@ -438,18 +438,6 @@ def register_global_singleton_context_hooks(example, globals)
438438
process(example, parent_groups, globals, :after, :context) { {} }
439439
end
440440

441-
def register_global_hook(prepend_or_append, position, *args, &block)
442-
scope, options = scope_and_options_from(*args)
443-
444-
if scope == :example || options.empty? || MetadataFilter.apply?(:all?, options, @owner.metadata)
445-
register_hook(prepend_or_append, position, scope, options, &block)
446-
else
447-
@owner.children.each do |group|
448-
group.hooks.register_global_hook(prepend_or_append, position, *args, &block)
449-
end
450-
end
451-
end
452-
453441
def register(prepend_or_append, position, *args, &block)
454442
scope, options = scope_and_options_from(*args)
455443

@@ -463,7 +451,8 @@ def register(prepend_or_append, position, *args, &block)
463451
return
464452
end
465453

466-
register_hook(prepend_or_append, position, scope, options, &block)
454+
hook = HOOK_TYPES[position][scope].new(block, options)
455+
ensure_hooks_initialized_for(position, scope).__send__(prepend_or_append, hook, options)
467456
end
468457

469458
# @private
@@ -564,11 +553,6 @@ def ensure_hooks_initialized_for(position, scope)
564553
end
565554
end
566555

567-
def register_hook(prepend_or_append, position, scope, options, &block)
568-
hook = HOOK_TYPES[position][scope].new(block, options)
569-
ensure_hooks_initialized_for(position, scope).__send__(prepend_or_append, hook, options)
570-
end
571-
572556
def process(host, parent_groups, globals, position, scope)
573557
hooks_to_process = globals.processable_hooks_for(position, scope, host)
574558
return if hooks_to_process.empty?

0 commit comments

Comments
 (0)