我正在使用FactoryGirl和Rspec进行测试。 如果为零,则模型在init之后设置外键。因此它使用另一个关联的数据。但我怎么测试呢? 通常我会使用工厂来创建这个对象,并使用stub_chain作为“self.user.main_address.country_id”。但是在创建此对象后,将调用initialize。我没有机会把它留下来。
after_initialize do
if self.country_id.nil?
self.country_id = self.user.main_address.country_id || Country.first.id
end
end
有什么想法吗?
答案 0 :(得分:8)
理想情况下,测试行为而不是实现更好。测试是否设置了外键而不是测试该方法是否被调用。
虽然,如果您想测试after_initialize
回调,这是一种有效的方法。
obj = Model.allocate
obj.should_receive(:method_here)
obj.send(:initialize)
Allocate将对象放入内存但不调用initialize
。设置期望后,您可以调用initialize并捕获方法调用。
答案 1 :(得分:5)
奥兰多的方法有效,而这是我想添加的另一种方法。 (使用新的rspec'期望'语法)
expect_any_instance_of(Model).to receive(:method_here)
Model.new
答案 2 :(得分:0)
另一种方法是重构代码以允许进行简单的单元测试。照原样,您的代码已接近我在回调中输入的代码量的上限:
curl_setopt($ch, CURLOPT_COOKIEJAR, $cookieFileName);
curl_setopt($ch, CURLOPT_COOKIEFILE, $cookieFileName);
如果增长更多,我将其提取到一个方法中,并将您的回调减少为一个方法调用:
after_initialize do
if self.country_id.nil?
self.country_id = self.user.main_address.country_id || Country.first.id
end
end
这里的好处是,测试after_initialize :init_country_id
def init_country_id
if self.country_id.nil?
self.country_id = self.user.main_address.country_id || Country.first.id
end
end
成为此时的另一种方法单元测试……对此一无所知。
现在您已经对行为进行了单元测试,如果您有疑问,还可以测试它是否被调用。 (像init_country_id
这样简单的事情不需要进行调用测试,IMO)
您可以使用gem shoulda-callback-matchers来测试您的回调实际上已按预期触发:
after_initialize :init_country_id