41

So Rails 3.1 comes with a little-known handy "rails g plugin new" generator, which gives you a skeleton suitable for a rails gem plugin. [http://guides.rubyonrails.org/plugins.html#or-generate-a-gemified-plugin]

One of the useful things this does, is set things up conveniently for testing with Test::Unit. It gives you a basic dummy Rails app that your tests can run in the context of, to test 'engine' behavior that only functions in the copy of a Rails app. (it puts it in ./test/dummy). But your tests are still in my_gem/test , the tests dont' live in the dummy app. And my_gem/test/test_helper.rb is there, written such that tests will be run in the context of the dummy app, booted over at ../dummy/config/environment.

I describe this because I think a lot of people don't know about this new generator, which sets things up so nicely.

But my question is, has anyone figured out how to do this with rspec instead? I have tried to follow the same principles DIY to set things up like this for rspec in a rails plugin gem, but am running into various confusing roadblocks, and am hoping maybe someone else has already figured it out (or would be interested in figuring it out for the rest of us, heh).

jrochkind
  • 22,799
  • 12
  • 59
  • 74

2 Answers2

95

Create the plugin without test-unit and specify the path for the dummy application:

rails plugin new foobar --skip-test-unit --dummy-path=spec/dummy

Add rspec-rails as a development dependency to the gemspec file (foobar.gemspec):

Gem::Specification.new do |s|
  .
  .
  .
  s.add_development_dependency "rspec-rails"
end

Run bundle install

Create a symlink from the dummy app to the plugin spec directory and run the Rspec install generator:

cd spec/dummy
ln -s ../../spec
rails generate rspec:install
cd -

Now edit spec/spec_helper.rb (or spec/rails_helper.rb in rails 4+, not sure about older versions) changing this line (line 3):

require File.expand_path("../../config/environment", __FILE__)

To this:

require File.expand_path("../dummy/config/environment", __FILE__)

Now you can run Rspec from the root of your plugin and it will pick up specs from the dummy application as well.

bundle exec rspec spec

I wrote about this in more detail, showing how to also set up capybara, spork and guard in a rails plugin with a dummy application:

https://web.archive.org/web/20130125091106/http://namick.tumblr.com/post/17663752365/how-to-create-a-gemified-plugin-with-rails-3-2-rspec

drewish
  • 9,042
  • 9
  • 38
  • 51
nathan amick
  • 1,133
  • 9
  • 7
  • 5
    For me, the line: `require File.expand_path("../../config/environment", __FILE__)` was located at `spec/rails_helper.rb` instead of `spec/spec_helper.rb`. Is this due to a change in Rspec? – J3RN Jul 29 '14 at 00:11
  • If you will keep dummy folder inside spec/ then rspec will find your spec files two times. First time for gem, second time for rails app, since patter there will match all spec files , regarding if they are under symlink or not. [--exclude-pattern](https://relishapp.com/rspec/rspec-core/v/3-3/docs/configuration/exclude-pattern) seems to work only together with --pattern. `config.pattern << ',!spec/dummy'` and alike seems not to work either The only solution that seems to be fixing this case is to have dummy folder outside of spec folder – Max Jun 26 '15 at 12:37
  • The link to the tumblr article is actually broken... @nathan-amick did you upload it somewhere else? – opsidao Feb 04 '16 at 15:55
  • As of Rails 5 (May 2 2017), I believe the flag is `--skip-test` instead of `--skip-test-unit`. – user2490003 May 03 '17 at 03:38
  • 1
    @max - I encountered the same issue. However, I was able to get it working with `--exclude-pattern "spec/dummy/spec/**/*_spec.rb"`. You can also add that line directly to your `.rspec` file so you don't have to type it out each time. I'm using `rspec 3.5.2` with Rails 5 – user2490003 Jun 17 '17 at 01:53
22

Just run rails plugin new <gemname> and then add rspec as development_dependency to gemspec file, and install it rspec --init.

Now move dummy sub folder from test to spec and add these to spec_helper:

ENV["RAILS_ENV"] = "test"

require File.expand_path("../dummy/config/environment.rb",  __FILE__)
require "rails/test_help"
require '<gemname>'

Rails.backtrace_cleaner.remove_silencers!

as they are in test_helper!

Hassan
  • 949
  • 7
  • 8