有足够的questions
与此主题相关,但没有一个提供practial
示例引用差异。
根据 Fowler的文章模拟不是存根,存根是独立于外部调用的假方法,而模拟是假对象,具有对调用的预编程反应。
Stub不能让您的测试失败,但Mocks可以。
模拟更具体,与对象相关:如果某些参数是 传递,然后对象返回某些结果。一个人的行为 对象被模仿或被模仿"。
Stubbing更通用,与方法相关:通常是一种存根方法 返回所有参数的结果总是相同。一个人的行为 方法是冻结的,罐装的或" stubbed"。
我们采取一个简单的test
案例。我们必须找到一个提供了id并与用户相关的Book
。
it "can find an Book that this user belongs to" do
project = Book.find( id: '22', email: user@test.com )
expect(project) to eq(some_data);
end
在上面的例子中......什么是存根,什么是模拟?如果我的示例无效,任何人都可以向我显示模拟和存根的example
。
答案 0 :(得分:1)
让我们举两个例子:
let(:email) { 'email' }
# object created from scratch
let(:mocked_book) { instance_double Book, email: email }
it 'check mock' do
expect(mocked_book.email).to eq email
end
#
let(:book) { Book.new }
it 'check stub' do
allow(book).to receive(:email) { email }
expect(book.email).to eq email
end
您的示例不相关:您不会测试有效记录,但您需要stub
才能返回mock
假设你需要测试一本书收到的方法,例如:
def destroy
@book = Book.find(params[:id])
if @book.destroyable?
@book.destroy
else
flash[:error] = "errr"
end
redirect_to books_path
end
您可以使用以下代码进行测试:
it 'is not destroyed if not destroyable' do
mocked_book = double 'book', destroyable?: false
allow(Book).to receive(:find).and_return mocked_book
expect(mocked_book).to_not receive :destroy
# here goes the code to trigger the controller action
end
it 'is destroyed if destroyable' do
mocked_book = double 'book', destroyable?: true
allow(Book).to receive(:find).and_return mocked_book
expect(mocked_book).to receive :destroy
# here goes the code to trigger the controller action
end
你可以在这里看到利弊:
缺点:模拟必须确切知道预期的方法是什么
专业人士:使用模拟器,您不需要真正创建对象并将其设置为使其适合某些条件