测试模型的Rails说'预期错误是真的'

Pra*_* KJ 1 ruby testing ruby-on-rails

我有一个网站,用户可以在注册时创建产品,产品可以有清单.

我有一个清单表,其中包含以下列: -

id  |  product_id  | content  |  archived 
Run Code Online (Sandbox Code Playgroud)

我是铁轨测试的新手.我在下面写了测试

  test 'should have content' do
    checklist = Checklist.new
    assert checklist.save
  end
Run Code Online (Sandbox Code Playgroud)

并使用以下命令运行测试

ruby -I test test/models/checklist_test.rb
Run Code Online (Sandbox Code Playgroud)

并且测试失败,预期的错误是真正的 错误.

是否因为问题可以使用user.product.checklists访问清单我必须首先填充灯具中的数据并调用那些测试中的数据?

编辑1

我在清单模型中没有任何验证.

class Checklist < ApplicationRecord belongs_to :product end

我加了!在测试中保存如下

  test 'should have content' do
    checklist = Checklist.new
    assert checklist.save!
  end
Run Code Online (Sandbox Code Playgroud)

并得到了这个错误

ActiveRecord :: RecordInvalid:验证失败:产品必须存在

因为表中有product_id.我不知道如何向rails测试提供数据.有帮助吗?

编辑2

编辑后如下所示消除错误.

class Checklist < ApplicationRecord belongs_to :product, optional: true end

但是我想用product现在测试模型.我不知道如何使用灯具为测试提供数据,好像没有我可以Checklist.new在测试中使用的外键.

既然它有外键我怎么能提供Checklist属于Product它本身所属的数据User

Tom*_*ord 5

checklist.savefalse如果由于checklist某种原因未能保存,将返回; 大概是因为验证失败了.

例如,也许您的app/models/checklists.rb内容包含:

validates :product_id, presence: true
Run Code Online (Sandbox Code Playgroud)

要么:

validates :content, length: { minimum: 10 }
Run Code Online (Sandbox Code Playgroud)

等等.在这个简单的场景中,您可以通过查看模型定义轻松确定错误; 但是对于更复杂的应用程序,您可以查看:checklist.errors.messages查看记录无法保存的原因列表.

从测试名称("应该有内容")来判断,我的猜测是它失败了因为content不能空白!

例如,要使此测试通过,您可能需要编写:

test 'should have content' do
  checklist = Checklist.new(content: 'hello world')
  assert checklist.save
end
Run Code Online (Sandbox Code Playgroud)

人们在测试此类事物时使用的一种常见方法是在工厂中定义"有效记录" ; 这使您可以显式测试无效记录,而不必在许多地方显式重新定义有效记录.例如,你可以这样做:

# test/factories/checklists.rb
FactoryBot.define do
  factory :checklist do
    content 'test content'
  end
end

# test/models/checklist_test.rb
test 'should have content' do
  checklist = build(:checklist, content: nil)
  refute checklist.save # Expecting this to FAIL!
  assert_includes "Content cannot be nil", checklist.errors
end
Run Code Online (Sandbox Code Playgroud)

(代码可能不是100%完整/准确;但你明白了)

  • @PraveenKJ在Rails 5中,`belongs_to`添加了对产品存在的验证.如果要将其关闭并使其成为可选项,则可以指定`optional:true`作为选项.在这里阅读更多内容:http://guides.rubyonrails.org/association_basics.html#optional (3认同)