Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

How to use RSpec's should_raise with any kind of exception?

People also ask

What is let in RSpec?

let generates a method whose return value is memoized after the first call. This is known as lazy loading because the value is not loaded into memory until the method is called. Here is an example of how let is used within an RSpec test. let will generate a method called thing which returns a new instance of Thing .


expect { some_method }.to raise_error

RSpec 1 Syntax:

lambda { some_method }.should raise_error

See the documentation (for RSpec 1 syntax) and RSpec 2 documentation for more.


RSpec 2

expect { some_method }.to raise_error
expect { some_method }.to raise_error(SomeError)
expect { some_method }.to raise_error("oops")
expect { some_method }.to raise_error(/oops/)
expect { some_method }.to raise_error(SomeError, "oops")
expect { some_method }.to raise_error(SomeError, /oops/)
expect { some_method }.to raise_error(...){|e| expect(e.data).to eq "oops" }

# Rspec also offers to_not:
expect { some_method }.to_not raise_error
...

Note: raise_error and raise_exception are interchangeable.

RSpec 1

lambda { some_method }.should raise_error
lambda { some_method }.should raise_error(SomeError)
lambda { some_method }.should raise_error(SomeError, "oops")
lambda { some_method }.should raise_error(SomeError, /oops/)
lambda { some_method }.should raise_error(...){|e| e.data.should == "oops" }

# Rspec also offers should_not:
lambda { some_method }.should_not raise_error
...

Note: raise_error is an alias for raise_exception.

Documentation: https://www.relishapp.com/rspec

RSpec 2:

  • https://www.relishapp.com/rspec/rspec-expectations/v/2-13/docs/built-in-matchers/raise-error-matcher

RSpec 1:

  • http://apidock.com/rspec/Spec/Matchers/raise_error
  • http://apidock.com/rspec/Spec/Matchers/raise_exception

Instead of lambda, use expect to:

   expect { some_method }.to raise_error

This is applies for more recent versions of rspec, i.e. rspec 2.0 and up.

See the doco for more.


The syntax changed recently and now it is:

expect { ... }.to raise_error(ErrorClass)

From version 3.3 on rspec-expections gem raises a warning for a blank raise_error without a parameter

expect { raise StandardError }.to raise_error # results in warning
expect { raise StandardError }.to raise_error(StandardError) # fine

This gives you a hint that your code may fail with a different error than the test intended to check.

WARNING: Using the raise_error matcher without providing a specific error or message risks false positives, since raise_error will match when Ruby raises a NoMethodError, NameError or ArgumentError, potentially allowing the expectation to pass without even executing the method you are intending to call. Instead consider providing a specific error class or message. This message can be supressed by setting: RSpec::Expectations.configuration.warn_about_potential_false_positives = false.