Question

I have a lot of cookbooks and they are heavily tested with ChefSpec. I have more than 800 specs and it has become a problem to run them every time before committing code, because on my machine it takes about 20 minutes to run them. That makes ~0.(6)s per spec, which is not much, but adds up to long amount of time.

Is there any possibility to run ChefSpec/RSpec tests in parallel or somehow else increase speed?

Was it helpful?

Solution

Update 4 Jan 2014: The following idea is now implemented inside ChefSpec (>= 3.1.2). See Faster Specs part in Readme.

================================

This is a excerpt from an blogpost that covers this topic with some more details.

RSpec allows to extend modules with your own methods and the idea is to write method similar to let, but which will cache the results across examples too. Create a *spec_helper.rb* file somewhere in your Chef project and add the following lines there:

module SpecHelper
  @@cache = {}
  def shared( name, &block )
    location = ancestors.first.metadata[:example_group][:location]
    define_method( name ) do
      @@cache[location + name.to_s] ||= instance_eval( &block )
    end
  end

  def shared!( name, &block )
    shared name, &block
    before { __send__ name }
  end
end

RSpec.configure do |config|
  config.extend SpecHelper
end

Values from @@cache are never deleted, and you can use same names with this block, so I also use location of the usage, which looks like that: "./cookbooks/my_cookbook/spec/default_spec.rb:3". Now change let( :chef_run ) into shared( :chef_run ) in your specs:

describe "example::default" do
  shared( :chef_run ) { ChefSpec::ChefRunner.new.converge described_recipe }
  [...]
end

And when running the tests you will now have to include the spec_helper.rb too:

rspec --include ./relative/path/spec_helper.rb cookbooks/*/spec/*_spec.rb
Licensed under: CC-BY-SA with attribution
Not affiliated with StackOverflow
scroll top