Rails 3教程Ch。 10.6 ex 5 rspec失败

时间:2011-09-28 20:15:05

标签: ruby-on-rails rspec

在解决练习5时,我遇到了与此question类似的问题。我根据给出的问题进行了重构,但仍然收到了失败:

1) UsersController DELETE 'destroy' as an admin user should not self-destruct
     Failure/Error: lambda do
       count should have been changed by 0, but was changed by -1
    # ./spec/controllers/users_controller_spec.rb:354:in `block (4 levels) in <top     (required)>'

我的规格:

  it "should destroy the user" do
    lambda do
      delete :destroy, :id => @user
    end.should change(User, :count).by(-1)
  end

  it "should redirect to the users page" do
    delete :destroy, :id => @user
    response.should redirect_to(users_path)
  end

  it "should not self-destruct" do
    lambda do
      delete :destroy, :id => @user.id
    end.should change(User, :count).by(0)
  end

和我的控制员:

def destroy
  @user = User.find(params[:id])
  if current_user == @user
    flash[:notice] = "You cannot destroy yourself"
  else
    @user.destroy
     flash[:success] = "User destroyed"  
  end
  redirect_to users_path
end

我已经检查了浏览器中的行为,它按预期工作。一如往常,任何帮助表示赞赏。谢谢!


更新后的工作代码:

describe "as an admin user" do

  before(:each) do
    @admin = Factory(:user, :email => "admin@example.com", :admin => "true")
    test_sign_in(@admin)
  end

  it "should have links to destroy a user" do
    get :index
    response.should have_selector("a", :content => "delete" )
  end

  it "should destroy the user" do
    lambda do
      delete :destroy, :id => @user
    end.should change{ User.count }.by(-1)
  end

  it "should redirect to the users page" do
    delete :destroy, :id => @user
    response.should redirect_to(users_path)
  end

  it "should not be allowed to delete itself" do
    lambda do
      delete :destroy, :id => @admin
    end.should_not change{ User.count }
  end
end

2 个答案:

答案 0 :(得分:1)

这也让我很久了。尝试更改语法:

should change(User, :count).by(-1)

为:

should change{ User.count }.by(-1)

或者尝试:

这稍微远离了本书,但您可以尝试更改语法。 RSpec对这种期望的建议是:

it "should destroy the user" do
  expect{
    delete :destroy, :id => @user
  }.to change{ User.count }.by(-1)
end

我认为其中更干净,更可读。你能提供一本书中的例子链接吗?

答案 1 :(得分:1)

我刚刚意识到我读了你发布的三个测试中的错误一个(如果你只发布了失败的测试,会更清楚:)

但是我很困惑,您的"it should not self destruct"测试与"it should destroy the user"完全相同:

it "should destroy the user" do
  lambda do
    delete :destroy, :id => @user
  end.should change(User, :count).by(-1)
end

it "should not self-destruct" do
  lambda do
    delete :destroy, :id => @user.id
  end.should change(User, :count).by(0)
end

您同时进行相同的测试,但期望得到不同的结果。我会再次看一下“它不应该自毁”,看看你的意思(我不确定)。

我猜想需要改变的是`change(xxxx).by(0)中的内容。什么是不应该通过测试改变?