Problem It takes a bit of time for my Rails tests to start, both RSpec and Cucumber.

Why This is because it has to load Rails before it can start running the test.

Consequences This dramatically slows down my TDD because I have to wait a few seconds after modifying my code. These seconds add up and it slows down my flow.

Solution There is a gem called Spork. It runs as a DRb server where it keeps the Rails environment between tests so you don’t have the startup cost. Both RSpec and Cucumber has command line options for the DRb.


Put into your Gemfile.

gem 'spork'

Then type this in your shell:

$ bundle install
$ spork cucumber --bootstrap
$ spork rspec --bootstrap

This will modify features/support/env.rb for Cucumber and spec/spec_helper.rb for RSpec. You just have to follow the instructions written in those files. Basically put all the original code that was there into the Spork.prefork block. This way it only gets executed once. If things break (in my case, nothing broke), you may need to put some statements into the other block, Spork.each_run.

Run spork. You may want to run them in separate shells.

$ spork rspec
$ spork cucumber

spork rspec will run on port 8989 and spork cucumber will run on port 8990. You need to modify the config files for RSpec and Cucumber so they are aware of the spork server.

For Cucumber add --drb --port=8990 to your config/cucumber.yml file. For example, I put the arguments in the variable std_opts:

rerun = File.file?('rerun.txt') ?'rerun.txt') : ""
rerun_opts = rerun.to_s.strip.empty? ? "--format #{ENV['CUCUMBER_FORMAT'] || 'progress'} features" : "--format #{ENV['CUCUMBER_FORMAT'] || 'pretty'} #{rerun}"
std_opts = "--format #{ENV['CUCUMBER_FORMAT'] || 'pretty'} --drb --port=8990 --strict --tags ~@wip"
default: <%= std_opts %> features
wip: --tags @wip:3 --wip features
rerun: <%= rerun_opts %> --format rerun --out rerun.txt --strict --tags ~@wip

For RSpec a line --drb to you .rspec file.

When you run rspec, it will automatically connect to the spork server and it should be a little faster. It should work the same way with cucumber, but for some reason it is throwing an exception on SystemExit. Other than that, it works fine.

You’ll probably notice a big difference now if you use automated testing. Using guard or autotest, you should see a significant difference in speed in your TDD.