0

如果我需要验证所有者范围内的猫名的唯一性,以便没有所有者可以拥有许多同名的猫,我可以使用它:

validates_uniqueness_of :name, scope: :owner_id

但是我如何验证猫是否拥有所有者的唯一性?

所以所有有主人的猫都有唯一的名字。

所有没有主人的猫都有唯一的名字。

所以它的范围类似于scope: self.owner.present?.

我可以在不使用自定义验证方法的情况下使用验证助手吗?

4

1 回答 1

1

conditions您可以为您的唯一性验证分配一个子句。请参阅文档,其中给出了以下示例:

class Article < ActiveRecord::Base
  validates_uniqueness_of :title, conditions: -> { where.not(status: 'archived') }
end

所以如果你想确保所有没有主人的猫的唯一性,你会写

validates_uniqueness_of :name, conditions: -> { where(owner_id: nil) }

或者,如果您想确保所有拥有主人的猫的名字都是唯一的,无论它们的主人是谁:

validates_uniqueness_of :name, conditions: -> { where.not(owner_id: nil) }

如果你只想做一个或另一个,那就行了。然而,如果你想同时做这两个,你会发现这两个条件都被检查了——而且实际上,你返回的是一个唯一性约束,它检查整个表,但是在两个查询中而不是一个。

所以,如果我们确实想要两个检查,我们需要确保只检查其中一个,我们可以使用if/unless修饰符来做到这一点:

validates_uniqueness_of :name, conditions: -> { where(owner_id: nil) },
    if: -> { owner_id.nil? }
validates_uniqueness_of :name, conditions: -> { where.not(owner_id: nil) },
    unless: -> { owner_id.nil? }

因此,现在,如果您的猫有一个所有者 ID,则将运行检查具有所有者 ID 的所有记录范围内的唯一性的验证。但如果它没有所有者 ID,则将启动其他验证。

这意味着要跳过更多的箍,但应该可以满足您的需要。

于 2021-05-23T14:21:01.337 回答