Reputation: 16288
I'm following this basic tutorial and it seems these tests are supposed to be run in like 2 seconds max, but I'm getting 41 seconds for 5 tests.
I ran ChefSpec with --profile
and this is the result
Top 8 slowest examples (41.17 seconds, 99.8% of total time):
webserver_test::default When run on CentOS 7.2.1511 installs httpd
5.21 seconds ./spec/unit/recipes/default_spec.rb:20
webserver_test::default When run on Ubuntu 14.04 converges successfully
5.17 seconds ./spec/unit/recipes/default_spec.rb:39
webserver_test::default When run on CentOS 7.2.1511 enables the httpd service
5.16 seconds ./spec/unit/recipes/default_spec.rb:24
webserver_test::default When run on Ubuntu 14.04 starts the apache2 service
5.15 seconds ./spec/unit/recipes/default_spec.rb:51
webserver_test::default When run on CentOS 7.2.1511 converges successfully
5.15 seconds ./spec/unit/recipes/default_spec.rb:16
webserver_test::default When run on Ubuntu 14.04 installs apache2
5.13 seconds ./spec/unit/recipes/default_spec.rb:43
webserver_test::default When run on CentOS 7.2.1511 starts the httpd service
5.11 seconds ./spec/unit/recipes/default_spec.rb:28
webserver_test::default When run on Ubuntu 14.04 enables apache2 service
5.1 seconds ./spec/unit/recipes/default_spec.rb:47
Finished in 41.26 seconds (files took 6.58 seconds to load)
8 examples, 0 failures
Upvotes: 1
Views: 477
Reputation: 5554
If you have large dirs or files in your repo (like .git
or vendor/bundle
, see du -chs *
for a full list) this may affect the run: chefspec uploads all of them to local temporary Chef server.
Add these to chefignore
to avoid uploading them.
This may not be relevant to your case directly but I just met a similar issue (chefspec run of 40 minutes on CI server vs less than 10 seconds on my laptop) so I feel I should leave the solution if anyone runs into this too.
Upvotes: 0
Reputation: 54249
There are a couple of issues:
As @smefju mentioned, caching can help though it is often just easier to combine multiple specs:
it "does httpd stuff" do
expect(chef_run).to enable_service 'httpd'
expect(chef_run).to start_service 'httpd'
end
This will only run the converge once and use it for both checks, rather than having them as two separate examples like in the tutorial. You can put any number of assertions in a single example, just understand that you will improve speed but reduce test isolation. In this case, probably worth it.
Upvotes: 6
Reputation: 2745
You didn't shared the code, but the most likely is that you does not have any cache mechanism for chef run.
Basically this code:
let(:chef_run) do
runner = ChefSpec::ServerRunner.new
runner.converge(described_recipe)
end
needs to converge machine in every spec and this is slow. You can consider using built-in mechanism for caching chef_run
result or build your own solution if you have more complex spec rules (for example caching for different attributes and services across the whole test suite).
Another part solution is to divide and execute specs in parallel. You can achieve it with parallel_tests gem.
Upvotes: 1