ruby-on-rails-3.1 - RSpec : Testing out models with methods that call update_attributes

标签 ruby-on-rails-3.1 rspec2 rspec-rails

RSpec 新手在这里。

我正在尝试测试我的模型,这些模型的方法使用 update_attributes更新其他模型的值。

我确信这些值保留在数据库中,但它们没有通过规范。

但是,当我包含类似 @user.reload 的内容时有用。

我想知道我是否做错了事情。具体来说,一个改变其他模型属性的模型应该如何测试?

更新代码:

describe Practice do

before(:each) do
    @user = build(:user)
    @user.stub!(:after_create)
    @user.save!

    company = create(:acme)
    course = build(:acme_company, :company => company)
    course.save!

  @practice = create(:practice, :user_id => @user.id, :topic => "Factors and Multiples" )
end

describe "#marking_completed" do

    it "should calculate the points once the hard practice is done" do
        @practice.question_id = Question.find(:first, conditions: { diff: "2" }).id.to_s
        @practice.responses << Response.create!(:question_id => @practice.question_id, :marked_results => [true,true,true,true])
        @practice.save!

        lambda {
            @practice.marking_completed
            @practice.reload # <-- Must add this, otherwise the code doesn't work
        }.should change { @practice.user.points }.by(20)
    end
end

结尾

实践.rb
def marking_completed       

# Update user points
user.add_points(100)
self.completed = true
self.save!

结尾

在用户.rb
def add_points(points)
self.points += points
update_attributes(:points => self.points)

结尾

最佳答案

发生的事情是用户对象缓存在@practice 变量上,因此需要在用户更新时重新加载。对于当前规范,您对此无能为力,但您可能需要考虑实际测试的内容。在我看来,您的规范适用于实践模型,这似乎很奇怪,但断言 should change { @practice.user.points }.by(20)真正描述用户行为。

我个人会在你的规范中更多地分离实践和用户模型,并独立测试它们的行为。

describe "#marking_completed" do
  before do
    @practice.question_id = Question.find(:first, conditions: { diff: "2" }).id.to_s
    @practice.responses.create!(:question_id => @practice.question_id, :marked_results => [true,true,true,true])
    @practice.save!
  end

  it "should calculate the points once the hard practice is done" do
    @practice.user.should_receive(:add_points).with(20).once
    @practice.marking_completed
  end
end

然后我会为 User 模型添加一个单独的测试:
describe User do
  it 'should add specified points to a user' do
    lambda { subject.add_points(100) }.should change { subject.points }.by(100)
  end
end

另一种旁注是不清楚是什么 Question.find正在返回,或者为什么用户的分数在您的测试中变化了 20。

关于ruby-on-rails-3.1 - RSpec : Testing out models with methods that call update_attributes,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/8954640/

相关文章:

design-patterns - SASS 样式表设计模式或其他资源?

ruby-on-rails - 使用前端服务器和不同机器上的音频文件在 LAN 上运行 Ruby on rails 应用程序的流式音频?

ruby-on-rails - 使用 Rails 将日历转换为表单?

ruby-on-rails - 在线运行 Rails 代码

unit-testing - Rspec : Testing MongoMapper query

ruby-on-rails - Rails 3教程第11章 "Validation failed: Email has already been taken"错误

ruby-on-rails - 获取未定义的方法 `empty?' for nil :NilClass in my test suite when I try to call a Rails path helper (*_path) using Rails, Rspec

ruby - 如何测试使用 rspec 的 block 的函数

ruby-on-rails - 使用 get 和 delete 运行 Rspec 测试时获取错误数量的参数(2 个为 0)

ruby-on-rails - RSpec redirect_to 和 return 与 redirect_to && return