How can shared examples be shared across gems?

Hi,

I have shared examples in a gem…

some_gem_name/spec/some_gem_name/shared_examples.rb

…where the shared examples are contained in a module, e.g.,

module SharedExamples

shared_examples_for …

end

How can I include these shared examples in tests in a different gem
that depends on my some_gem_name, above? Maybe I can refer to the
shared examples in my dependent gem’s spec_helper?

Thanks,

Lille

On Dec 11, 2011, at 4:02 PM, Lille wrote:

shared_examples_for …

end

How does this even work? shared_examples_for is not defined in Module,
so unless you’re leaving something important out, that should raise an
error.

How can I include these shared examples in tests in a different gem
that depends on my some_gem_name, above? Maybe I can refer to the
shared examples in my dependent gem’s spec_helper?

There are two ways you can do this:

shared_examples “stuff” do
before { … }
let(:name) { value }
it “does something” do
# …
end
end

As long as this file is required somewhere (only once, please) you can
use those examples in your gem or any other gem:

describe Something do
it_behaves_like “stuff”
end

You can also define a module:

module SharedExamples
extend RSpec::Core::SharedContext
before { … }
let(:name) { value }
it “does something” do
# …
end
end

Now you can do a standard Ruby include

describe Something do
include SharedExamples
end

see
https://www.relishapp.com/rspec/rspec-core/docs/example-groups/shared-examples
see
http://rubydoc.info/github/rspec/rspec-core/master/RSpec/Core/SharedContext

HTH,
David

Thank you.

Here is what I did to conform my gem spec to the conventions suggested
at
https://www.relishapp.com/rspec/rspec-core/docs/example-groups/shared-examples

my spec/spec_helper.rb…

$LOAD_PATH.unshift(File.dirname(FILE))
$LOAD_PATH.unshift(File.join(File.dirname(FILE), ‘…’, ‘lib’))

Dir[“spec/support/**/*.rb”].each {|f| require f} # this did not

work…

require ‘rubygems’
require ‘rum_92265’
require ‘rspec’
require ‘rspec/autorun’
require ‘support/shared_examples’ # this did

now, at the top of in lib/rum_92265.rb…

require “rum_92265/version”
require File.dirname(FILE) + “/…/spec/support/shared_examples.rb”

finally, here are the top lines of the spec/support/
shared_sample.rb…

extend RSpec::Core::SharedContext

shared_examples_for “Rum92265::A3::PartB” do

Anyway, I hadn’t seen any gems with shared example groups exposed, so
this was the best I could come up with – it worked. It seems weird to
require shared_samples.rb from the lib directory, but I couldn’t see
where else – gemspec, for example? – to require it.

Lille

On Dec 13, 2011, at 6:30 PM, Lille wrote:

I moved your post to the bottom. Please read
Top Posting and Bottom Posting and please bottom post or inline post
so readers can more easily follow the thread.

shared examples in my dependent gem’s spec_helper?

before { … }
end

seehttps://www.relishapp.com/rspec/rspec-core/docs/example-groups/shared…
seehttp://rubydoc.info/github/rspec/rspec-core/master/RSpec/Core/SharedC…

HTH,
David

Thank you.

Here is what I did to conform my gem spec to the conventions suggested
at
https://www.relishapp.com/rspec/rspec-core/docs/example-groups/shared-examples

my spec/spec_helper.rb…

$LOAD_PATH.unshift(File.dirname(FILE))
$LOAD_PATH.unshift(File.join(File.dirname(FILE), ‘…’, ‘lib’))

You don’t need to modify the ^^ LOAD_PATH ^^ here - it’s already done
for you by RSpec.

Dir[“spec/support/**/*.rb”].each {|f| require f} # this did not work…

I’m assuming you’re using Ruby 1.9, which does not include “.” on the
LOAD_PATH (which is assumed by Dir[“spec/support/**/*.rb”]). Either of
these would work:

Dir[“./spec/support//*.rb"].each {|f| require f}
Dir["support/
/*.rb”].each {|f| require f}

I’ll update the docs on relishapp.com accordingly.

require File.dirname(FILE) + “/…/spec/support/shared_examples.rb”
This ^^ is going to get you into trouble because Ruby doesn’t see
/path/to/x/…/spec/support/shared_examples.rb and
/path/to/spec/support/shared_examples.rb as the same path (even though
they end at the same file). This means that your users will likely end
up requiring shared_examples.rb twice, which makes bad things happen.

I’d recommend modifying and relying on the LOAD_PATH instead. More
below.

finally, here are the top lines of the spec/support/
shared_sample.rb…

extend RSpec::Core::SharedContext

shared_examples_for “Rum92265::A3::PartB” do

You don’t need both “extend RSpec::Core::SharedContext” and
“shared_examples_for”. Just one or the other.

Anyway, I hadn’t seen any gems with shared example groups exposed, so
this was the best I could come up with – it worked. It seems weird to
require shared_samples.rb from the lib directory, but I couldn’t see
where else – gemspec, for example? – to require it.

Lille

If the idea here is to expose shared_examples to users of your gem, I’d
actually store them under lib. Something like:

lib/rum_92265/spec_support.rb # requires
rum_92265/spec_support/shared_examples.rb
lib/rum_92265/spec_support/shared_examples.rb

Now you can require ‘rum_92265/spec_support’ in your own
spec/spec_helper.rb, and you can tell your users to do the same.

HTH,
David

Here is what I did to conform my gem spec to the conventions suggested
athttps://www.relishapp.com/rspec/rspec-core/docs/example-groups/shared…

my spec/spec_helper.rb…

$LOAD_PATH.unshift(File.dirname(FILE))
$LOAD_PATH.unshift(File.join(File.dirname(FILE), ‘…’, ‘lib’))

You don’t need to modify the ^^ LOAD_PATH ^^ here - it’s already done for you by
RSpec.

OK - I made this change, thanks…

finally, here are the top lines of the spec/support/
shared_sample.rb…

extend RSpec::Core::SharedContext

shared_examples_for “Rum92265::A3::PartB” do

You don’t need both “extend RSpec::Core::SharedContext” and
“shared_examples_for”. Just one or the other.

…and made this change…

If the idea here is to expose shared_examples to users of your gem, I’d actually
store them under lib. Something like:

lib/rum_92265/spec_support.rb # requires
rum_92265/spec_support/shared_examples.rb
lib/rum_92265/spec_support/shared_examples.rb

Now you can require ‘rum_92265/spec_support’ in your own spec/spec_helper.rb,
and you can tell your users to do the same.

…finally, I did this, too. These steps added up to a successful
result for me.

Thank you very much for your detailed and helpful response.

Lille