Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Rspec `eq` vs `eql` in `expect` tests

Tags:

ruby

rspec

What is the difference between using eq and eql in rspec tests? Is there a difference between:

it "adds the correct information to entries" do   # book = AddressBook.new # => Replaced by line 4   book.add_entry('Ada Lovelace', '010.012.1815', '[email protected]')   new_entry = book.entries[0]    expect(new_entry.name).to eq('Ada Lovelace')   expect(new_entry.phone_number).to eq('010.012.1815')   expect(new_entry.email).to eq('[email protected]') end 

and:

it "adds the correct information to entries" do   # book = AddressBook.new # => Replaced by line 4   book.add_entry('Ada Lovelace', '010.012.1815', '[email protected]')   new_entry = book.entries[0]    expect(new_entry.name).to eql('Ada Lovelace')   expect(new_entry.phone_number).to eql('010.012.1815')   expect(new_entry.email).to eql('[email protected]') end 
like image 930
austinthesing Avatar asked Oct 03 '15 19:10

austinthesing


2 Answers

There are subtle differences here, based on the type of equality being used in the comparison.

From the Rpsec docs:

Ruby exposes several different methods for handling equality:  a.equal?(b) # object identity - a and b refer to the same object a.eql?(b) # object equivalence - a and b have the same value a == b # object equivalence - a and b have the same value with type conversions] 

eq uses the == operator for comparison, and eql ignores type conversions.

like image 92
stef Avatar answered Sep 29 '22 06:09

stef


The differences are subtle.eq is the same as the ruby implementation of ==. On the other hand eql is the same as the ruby implementation of eql?.

eq checks object equivalence and will type cast to convert different object to the same type.

Two objects are equivalent if they are of the same class and have the same value but they are not necessarily the same object in memory.

expect(:my_symbol).to eq(:my_symbol) # passes, both are identical. expect('my string').to eq('my string') # passes, objects are equivalent  expect(5).to eq(5.0) # passes, Objects are not equivalent but was type cast to same object type.  

eql checks object equivalence and does not try type casting.

expect(:my_symbol).to eql(:my_symbol) # passes, both are identical. expect('my string').to eql('my string') # passes, objects are equivalent but not identical  expect(5).to eql(5.0) # fails, Objects are not equivalence, did not try to type cast 

equal checks object identity. Two object are identical if they are the same object meaning they have same object id (share the same address in memory).

expect(:my_symbol).to equal(:my_symbol) # passes, both are identical. expect('my string').to equal('my string') # fails, objects are equivalent but not identical expect(5).to equal(5.0) # fails, objects are not equivalent and not identical 
like image 29
Faruk Hossain Avatar answered Sep 29 '22 07:09

Faruk Hossain