在具有has_many关系的模型上定义条件能力

时间:2013-06-18 19:30:44

标签: ruby-on-rails ruby-on-rails-3 cancan

首先,我的协会:

Form has_many :agreements
Agreement belongs_to :student

当我的某个协议属于当前用户时,我正在尝试定义当前用户can :read, Form的功能。

我试图像这样定义这种能力:

Ability.rb:

can :read, Form do |f|
  f.agreements.select { |a| a.student_id == user.id }.nil? == false
end

我也试过了:

can :read, Form, agreements: { student_id:  user.id }

不幸的是,第一个解决方案允许所有学生查看所有表格,即使他们没有附加到其中一个表格协议。第二种解决方案不允许任何学生查看表格,即使这些表格附在表格协议之一上。

我做错了什么?

1 个答案:

答案 0 :(得分:1)

这条线不好:

f.agreements.select { |a| a.student_id == user.id }.nil? == false

原因是#select将始终返回一个数组。如果没有student_iduser.id匹配的协议,那么您将获得一个空数组([])。但是任何数组(包括空数组)上的#nil?始终为false。所以这一行总是评估为真。

修复非常简单。使用rails方法#blank?代替#nil?。如果对象为nil或者empty,则返回true。 [].empty?会返回true

tldr:将上一行更改为

f.agreements.select { |a| a.student_id == user.id }.blank? == false