validation相关对象的最大数量

我有一个帐户模型和一个用户模型:

class Account < ActiveRecord::Base has_many :users end class User < ActiveRecord::Base belongs_to :account end 

用户属于某个帐户,并且帐户具有用户最大值(每个帐户不同)。 但是,如何在向帐户添加新用户时validation是否未达到此最大值?

首先,我尝试在用户上添加validation:

 class User < ActiveRecord::Base belongs_to :account validate :validate_max_users_have_not_been_reached def validate_max_users_have_not_been_reached return unless account_id_changed? # nothing to validate errors.add_to_base("can not be added to this account since its user maximum have been reached") unless account.users.count < account.maximum_amount_of_users end end 

但这只有在我一次添加一个用户时才有效。

如果我通过@account.update_attributes(:users_attributes => ...)添加多个用户,即使只有一个用户的空间,它也会直接通过。

更新:

只是为了澄清:当前validation方法validationaccount.users.count小于account.maximum_amount_of_users 。 例如,例如, account.users.count为9, account.maximum_amount_of_users为10,则validation将通过,因为9 <10。

问题是,在将所有用户写入数据库之前,从account.users.count返回的计数不会增加。 这意味着同时添加多个用户将通过validation,因为用户计数将一直相同,直到它们全部经过validation。

正如askegg指出的那样,我是否应该在帐户模型中添加validation? 那怎么办呢?

如果您调用account.users.size而不是account.users.count它还将包括已构建但未保存到数据库的用户。

但是,这并不能完全解决您的问题。 当您在用户中呼叫account ,它不会返回@account指向的同一帐户实例,因此它不知道新用户。 我相信这将在Rails 3中“修复”,但与此同时我可以想到几个解决方案。

如果您在添加用户的同时保存帐户(我假设您正在调用update_attributes ),那么validation可以在那里进行。

 # in account.rb def validate_max_users_have_not_been_reached errors.add_to_base("You cannot have more than #{maximum_amount_of_users} users on this account.") unless users.size < maximum_amount_of_users end 

我不确定您是如何保存关联模型的,但如果帐户validation失败,则不应保存。

另一种解决方案是在更新用户属性时将user.account实例重置为self。 您可以在users_attributes setter方法中执行此操作。

 # in account.rb def users_attributes=(attributes) #... user.account = self #... end 

这样,用户的帐户将指向同一个帐户实例,因此account.users.size应返回金额。 在这种情况下,您将在用户模型中保留validation。

这是一个棘手的问题,但希望这给你一些如何解决它的想法。

它传递的原因是因为update_attributes没有通过validation。

此外 – 您的逻辑仅根据允许的最大值检查现有帐户数。 考虑到尝试添加的用户数量,没有计算。 我认为这个逻辑更多地属于帐户模型(?)。