覆盖自定义验证

时间:2018-07-05 08:56:55

标签: ruby-on-rails rspec

对于ruby on rails,我有一个player模型,其中有许多games。但是,玩家应至少玩三局。我有一个自定义验证器,如果没有三款游戏,则会增加错误。通过在player模型中进行声明,我可以创建一个拥有三场比赛的玩家

accepts_nested_attributes_for :games

并使用玩家和游戏属性的嵌套哈希创建player及其游戏。

但是出于测试目的,有时我有时想一次使用rspec这样的代码一次添加一个游戏

player = create: :player
game = create :game
player.games << game

但这不会起作用,因为create :player会触发自定义验证,因此失败,因为它没有三局游戏。

有没有办法做到这一点。如果无法执行此操作,则只能通过制作嵌套的哈希值来测试对特定游戏的敏感性,因为密钥的变化很深,因此很难看到测试的结果。

2 个答案:

答案 0 :(得分:0)

您可以使用自定义方法来持久化对象

factory :player do
  to_create {|instance| instance.save(validate: false) }
end

https://github.com/thoughtbot/factory_bot/blob/master/GETTING_STARTED.md#custom-methods-to-persist-objects

答案 1 :(得分:0)

我将建议跳过验证,即使在您的Rspec中也是如此,除非无法避免。如果可能,请修改您的Rspecs以遵守验证。

您可以执行以下操作:

let(:player) { build(:player) }
let(:game) { create(:game) }
let(:another_game) { create(:game) }
let(:one_more_game) { create(:game) }

it 'test something' do
  player.games += [game]

  # Do your stuff

  player.games += [another_game]

  # Do some more stuff

  player.games += [one_more_game]

  # and now that `player` object is valid, you can do:
  player.save!

  # Check your expectations here
end

注意:

  • 我不是在没有游戏的情况下创建player对象,而是在构建player对象,这是允许的。除非确实需要,否则您无需创建任何东西。
  • 我已使用let修改了您的变量。它们更适合Rspec。

我希望这可以解决您的问题。如果没有,请显示更多您的Rspec代码,我们可以尝试对其进行修改以支持验证。