How To Use The VCR Gem With Rails And Rspec

So yesterday I spent way too much time trying to make this really cool VCR gem work with my rspec tests. The problem was that most of the tutorials out there were pretty outdated, and things have changed a bit.

The VCR gem is really useful if you have methods that need to make an api request. You don’t want to make api requests during tests, especially if the api has some kind of rate limit (I’m looking at you Twitter!).

So what you could do is create a text file mocking the response you get from the web service you’re making the api to and do the tests that way, or you can use the VCR gem! The VCR gem makes an api request once, and records the response to a cassette, which it then uses in future tests. Clever, no?

Here’s how you set up the VCR gem in your Rails App with Rspec:

Get The Gems

In your Gemfile, make sure to add the vcr gem along with a gem that does the HTTP interaction. The VCR gem supports the following HTTP request services, which also have nice gems:

  • FakeWeb
  • WebMock
  • Typhoeus

For a complete list of these, check out the VCR gem page on Github. I will be using Typhoeus in my example, so my Gemfile includes the vcr and the typhoeus gems:

# Gemfile
....
gem 'typhoeus', '0.4.2'

group :development, :test do
  ......
  gem 'vcr', '2.2.5'
end

Don't forget to run 'bundle install' after you add these gems!

Set Up Support

Create a spec/support directory, and add a vcr_setup.rb file to it. In the vcr_setup.rb file, add your VCR configuration.

# spec/support/vcr_setup.rb
VCR.configure do |c|
  #the directory where your cassettes will be saved
  c.cassette_library_dir = 'spec/vcr'
  # your HTTP request service. You can also use fakeweb, webmock, and more
  c.hook_into :typhoeus
end

Note that I also added a spec/vcrdirectory. This is where my cassettes will be saved.

Take a look at the documentation for additional configuration options.

Add some test!

Now you are ready to add your Rspec tests. Simply put the web request part of your tests in a VCR.use_cassette block.

# spec/model/your_model_spec.rb
describe YourModel do
  describe '#call_api" do
     it "gets a response from an api" do
       VCR.use_cassette 'model/api_response' do
          response = call_api(api_url)
          response.first.should == "hello world"
       end
     end
  end
end

When you run this test for the first time, check your spec/vcr directory. You will see a new directory called ‘model’, and in it will be the api_response.yml file, which will include the response from the api that you just called. Now, every time the test runs, that cassette will be used instead of making the actual api call.

Enjoy the article? Join over 14,500+ Swift developers and enthusiasts who get my weekly updates.

  • Matt

    Haha I was just looking for tutorials on VCR and your post was on the first page of results. Very nicely done, Natasha!

  • rick

    when i run this test i get error as

    E:company_infoem-ftpd-masterspecmodel>rspec fake_spec.rb

    C:/Ruby193/lib/ruby/gems/1.9.1/gems/rspec-core-2.12.0/lib/rspec/core/configurati

    on.rb:784:in load': E:/company_info/em-ftpd-master/spec/model/fake_spec.rb:1: s

    yntax error, unexpected keyword_do_block, expecting keyword_end (SyntaxError)

    VCR.use_cassette 'mod... do

    ... ^

    E:/company_info/em-ftpd-master/spec/model/fake_spec.rb:1: syntax error, unexpect

    ed tIDENTIFIER, expecting keyword_end

    response.first.should == "hello ...

    ... ^

    E:/company_info/em-ftpd-master/spec/model/fake_spec.rb:1: syntax error, unexpect

    ed tAMPER

    ...esponse.first.should == "hello world"

    ... ^

    E:/company_info/em-ftpd-master/spec/model/fake_spec.rb:1: syntax error, unexpect

    ed keyword_end, expecting $end

    endndendnd

    ... ^

    from C:/Ruby193/lib/ruby/gems/1.9.1/gems/rspec-core-2.12.0/lib/rspec/cor

    e/configuration.rb:784:in block in load_spec_files’

    from C:/Ruby193/lib/ruby/gems/1.9.1/gems/rspec-core-2.12.0/lib/rspec/cor

    e/configuration.rb:784:in each'

    from C:/Ruby193/lib/ruby/gems/1.9.1/gems/rspec-core-2.12.0/lib/rspec/cor

    e/configuration.rb:784:in load_spec_files’

    from C:/Ruby193/lib/ruby/gems/1.9.1/gems/rspec-core-2.12.0/lib/rspec/cor

    e/command_line.rb:22:in run'

    from C:/Ruby193/lib/ruby/gems/1.9.1/gems/rspec-core-2.12.0/lib/rspec/cor

    e/runner.rb:69:in run’

    from C:/Ruby193/lib/ruby/gems/1.9.1/gems/rspec-core-2.12.0/lib/rspec/cor

    e/runner.rb:8:in `block in autorun’

    what should i do

  • Alex

    It seems to be an excellent article, but I am new at Ruby, so don’t know correctly how to do. Would you help?

  • This was very helpful, thanks šŸ™‚