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

Make rspec-expectations and rspec-mocks APIs available in before(:suite) hooks #1986

Merged
merged 1 commit into from
Jun 18, 2015

Conversation

JonRowe
Copy link
Member

@JonRowe JonRowe commented Jun 16, 2015

Currently users get errors if they try to use rspec-expectations or rspec-mocks APIs (e.g. expect(x).to y or allow(x).to receive) in a before or after :suite hook. It's not a common need (and not something I've ever wanted!) but for consistency/parity with the other hook types they should be available. It looks like the hooks are intended to run in the context of a SuiteHookContext object but somehow it's actually being run in the context of nil (woops!).

See rspec/rspec-mocks#966 for an example use case.

@JonRowe
Copy link
Member

JonRowe commented Jun 16, 2015

^^ found and done

RSpec.configuration.__send__(registration_method, :suite) { run_context = self }
RSpec.configuration.with_suite_hooks { }
expect(run_context).to be_a ExampleGroup
end
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I think it's worth adding some lines to this (or perhaps making a new spec) showing that rspec-mocks and rspec-expectations APIs can be used from within the hook. Ultimately that's the bug we're trying to fix. l think that as rspec-core currently works, any block evaluated in the context of an ExampleGroup instance would support those APIs but there's no guarantee that will always be true.

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

See below :)

@JonRowe JonRowe force-pushed the run_suite_hooks_in_an_example_group branch from e719b40 to ab7cc1c Compare June 17, 2015 23:37

it 'allows access to rspec-mocks methods within the hook' do
run = false
RSpec.configuration.__send__(registration_method, :suite) { double('something'); run = true }
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I'm surprised this works...I assume you'd have to wrap the double call in a with_temporary_scope.

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Why? They're not using the proxy space so they're harmless on their own right?

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I see why it works now...

  • A bare double with no allowances or expectations does not trigger the The use of doubles or partial doubles from rspec-mocks outside of the per-test lifecycle is not supported. (RSpec::Mocks::OutsideOfExampleError) error. So double('foo') is OK.
  • Even if you change to double('foo', :msg => "val") it still passes because there is an active rspec-mocks scope here since this is running inside and rspec example.

For a before(:suite) hook declared in spec_helper, double('foo', :msg => "val") does fail as I would expect.

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Do you want me to add a temporary scope? As this is currently demoing just access to the api I'm ok with this as is..

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I don't care much. Mostly I was surprised/confused by it. However, given I as surprised by it and rspec-mocks features don't work in :suite hooks normally without the scope, I think it's worth adding it to prevent future confusion.

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Added.

@myronmarston
Copy link
Member Author

LGTM

All other types of hooks are run in the context of example group
during an individual example group or examples run (respectively),
as a suite hook uses a special special sub class of example to run in
it wasn't even being setup correctly with an example group so they ran
in the context of nil. fixed.
@JonRowe JonRowe force-pushed the run_suite_hooks_in_an_example_group branch from ab7cc1c to 53a598b Compare June 18, 2015 03:02
@myronmarston
Copy link
Member Author

LGTM

JonRowe added a commit that referenced this pull request Jun 18, 2015
Make rspec-expectations and rspec-mocks APIs available in `before(:suite)` hooks
@JonRowe JonRowe merged commit a7c3f4f into master Jun 18, 2015
@JonRowe JonRowe deleted the run_suite_hooks_in_an_example_group branch June 18, 2015 06:01
@myronmarston
Copy link
Member Author

Should we backport this to 3-3-maintenance?

@JonRowe
Copy link
Member

JonRowe commented Jun 18, 2015

Done.

MatheusRich pushed a commit to MatheusRich/rspec-core that referenced this pull request Oct 30, 2020
…e_group

Make rspec-expectations and rspec-mocks APIs available in `before(:suite)` hooks
yujinakayama pushed a commit to yujinakayama/rspec-monorepo that referenced this pull request Oct 6, 2021
…hooks_in_an_example_group

This commit was imported from rspec/rspec-core@45f2cd9.
Sign up for free to subscribe to this conversation on GitHub. Already have an account? Sign in.
Labels
Projects
None yet
Development

Successfully merging this pull request may close these issues.

3 participants