【问题标题】:How to test a before_save method including accossioations with rspec如何测试 before_save 方法,包括与 rspec 的关联
【发布时间】:2010-08-08 11:16:28
【问题描述】:

我在测试以下模型时遇到问题:

class Bill < ActiveRecord::Base
  belongs_to :consignee
  before_save :calc_rate

  def calc_rate
    self.chargeableweight = self.consignee.destination.rate * self.weight
  end
end

收货人型号:

class Consignee < ActiveRecord::Base
  belongs_to :destination
  has_many :bills
end

控制器还没有被触及。

应用程序的行为是正确的(后续问题:该解决方案是否存在任何性能问题?) - 但测试中断。

当你没有时你有一个 nil 对象 期待它!你可能已经预料到了 数组的实例。发生错误 在评估 nil 时。*

谢谢你的建议, 丹尼

更新:

这个账单测试打破了工厂女孩:

describe Bill do

  it "should call the calc_rate method" do
    bill = Factory.build(:bill)
    bill.save!
    bill.should_receive(:calc_rate)
  end
end

你没想到的是一个 nil 对象!

工厂:

Factory.define :destination do |f|
  f.airport_code "JFK"
end

Factory.define :consignee do |f|
  ...
  f.association :destination
end


Factory.define :bill do |f|
  f.association :consignee
  f.weight 10
  f.chargeableweight 20.0
  f.after_create do |bill|
    bill.calc_rate
end

【问题讨论】:

  • 粘贴你的测试用例...

标签: ruby-on-rails ruby unit-testing rspec


【解决方案1】:
describe Consignee do
  it "should calculate the rate" do
    #pending
    #make sure this spec is passing first, so you know your calc_rate method is fine.
  end

  it "should accept calc_rate before save" do
    cosignee = mock("Consignee")
    consignee.should_receive(:calc_rate).and_return(2) # => stubbing your value
  end
end

我没有准备一个 Rails 应用程序来测试这段代码,但这应该能让你接近。另外,假设chargeable_rate、weight等列是模型上的列,你不需要调用self。如果没有可用的实例方法或该名称的变量,Ruby 将隐含地期望 self ,它将自动查找类方法。

【讨论】:

  • 感谢您的快速回答,杰德。很抱歉不清楚。我改变了问题 - 见上文
  • 您的目标工厂期望方法速率,但这并未在您的目标工厂中定义。这至少是我看到的一个问题。如果没有堆栈跟踪,很难知道它在哪里调用 nil。
猜你喜欢
  • 1970-01-01
  • 2023-03-10
  • 2017-01-17
  • 2022-01-11
  • 1970-01-01
  • 2017-11-18
  • 1970-01-01
  • 1970-01-01
  • 2016-06-28
相关资源
最近更新 更多