我有一个名为ResetPassword的服务对象,它处理ResetPassword Controller创建操作的所有逻辑。我也已经测试了服务对象。我应该模拟服务对象吗?我认为我应该准备好测试,它会减少运行规格。我目前为控制器的测试代码如下。不确定是否应该这样写。
require 'spec_helper'
describe ResetPasswordController do
describe "POST create" do
context "when email matches a user" do
let(:user) { Fabricate(:user) }
it "calls password_reset on PasswordReset" do
ResetPassword.stub(:reset_password)
ResetPassword.any_instance.should_receive(:reset_password)
post :create, email: user.email
end
it "redirects to root path" do
post :create, email: user.email
expect(response).to redirect_to root_path
end
end
context "when email doesn't match a user" do
it "redirects to new"
it "displays a flash error"
end
end
end
答案 0 :(得分:0)
我认为你应该在控制器中模拟服务,但是通过在类上注入模拟而不是存根来模拟它或any_instance
你的控制器看起来像这样
class ResetPasswordController < ApplicationController
def create
reset_password_service.reset_password(params[:email])
end
def reset_password_service
@reset_password_service ||= ResetPassword.new
end
def reset_password_service=(val)
@reset_password_service = val
end
end
然后在您的规范中,您可以
before { controller.reset_password_service = password_service }
let(:password_service) { double("PasswordService", reset_password: nil) }
it "does something good" do
post :create, email: "foo"
expect(password_service).to have_received(:reset_password).with("foo")
end
甚至更好,请改用instance_double
。这也将检查存根类实际上是否存在存根方法。这可以从RSpec 3.0.0.beta *
let(:password_service) { instance_double(PasswordService, reset_password: nil) }