anti-k anti-k - 2 months ago 14
Ruby Question

How to set a shared example?

I'm just learning to write specs in ruby, and rails. So I do have two similar models that act similar when voted: question and answer. So I try to not duplicate code and write shared example for this two.

RSpec.shared_examples_for 'User Votable' do

let!(:user){ create :user }
let!(:sample_user){ create :user }
let!(:vote){ create :vote, user: user, votable: votable, vote_field: 1}

it 'user different from resource user is accapteble' do
expect(votable.user_voted?(sample_user)).to be_falsy
end

it 'user similar to resource user is accapteble' do

expect(votable.user_voted?(user)).to be_truthy
end

end


And a test itself

describe 'user_voted?' do
def votable
subject{ build(:question)}
end
it_behaves_like 'User Votable'
end


The last it in this spec fails( I think because of subject - it does not change when I create a vote)
So I would be very happy if I could manage and understand how to do it right way. And very thankful for any advice

Also when I try to use mock like this, it complains on not having primary key

allow(:question){create :question}

Failures:


1) Question user_voted? behaves like User Votable user similar to resource user is accapteble
Failure/Error: expect(votable.user_voted?(user)).to be_truthy

expected: truthy value
got: false
Shared Example Group: "User Votable" called from ./spec/models/question_spec.rb:23

Answer

Instead of having a votable method could you set the subject as such:

it_behaves_like 'User Votable' do
  subject { build(:question) }
end