Rails的基于部门CanCanCan资源的能力
Posted
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了Rails的基于部门CanCanCan资源的能力相关的知识,希望对你有一定的参考价值。
我有两个用户类型管理员和普通用户
我有以下部门
- 前厅(例如,ID为1)
- 后台(例如,ID为2)
- 管理员(例如,ID为3)
我有一个模型一个名为Entry这需要USER_ID,部门标识,CUSTOMER_ID
Admin用户拥有所有部门和所有项目的完全控制CRUD
普通用户是针对各个科室创建和拥有各自部门的项目CRU控制
当我创建一个从普通用户的条目(例如,ID为2)帐户,我得到了正确的设置CUSTOMER_ID,部门标识,USER_ID的表中。该用户的能力只有一个条目can_create_entry(current_user.id,CUSTOMER_ID,部门标识),例如,(1,1,2),用于前台办公普通用户帐户。
当我创建管理员的条目(例如,ID为1)的帐户,我得到在表中的customer_id,DEPARTMENT_ID,USER_ID为(1,1,1)文我试图创建一个后台管理部门的ID是一款入门2。
当我检查了管理员用户的能力列表;我发现有条目能力即重复,
#<CanCan::Rule:0x0000000b61fd18 @match_all=false, @base_behavior=true, @actions=[:create], @subjects=[Entry(Table doesn't exist)], @conditions={:user_id=>1, :customer_id=>2, :department_id=>1}, @block=nil>
#<CanCan::Rule:0x0000000b61fd18 @match_all=false, @base_behavior=true, @actions=[:create], @subjects=[Entry(Table doesn't exist)], @conditions={:user_id=>1, :customer_id=>2, :department_id=>2}, @block=nil>
#<CanCan::Rule:0x0000000b61fd18 @match_all=false, @base_behavior=true, @actions=[:create], @subjects=[Entry(Table doesn't exist)], @conditions={:user_id=>1, :customer_id=>2, :department_id=>3}, @block=nil>
而对于普通用户,我只有一个入口
#<CanCan::Rule:0x0000000b61fd18 @match_all=false, @base_behavior=true, @actions=[:create], @subjects=[Entry(Table doesn't exist)], @conditions={:user_id=>2, :customer_id=>2, :department_id=>1}, @block=nil>
请帮我解决了管理员角色的问题。
编辑:ability_base.rb
class AbilityBase
include CanCan::Ability
...
def can_read_entries(customer_id, department_id)
can :read, Entry, :customer_id => customer_id, :department_id => department_id
end
def can_create_entries(customer_id, department_id,user_id)
can :create, Entry, :customer_id => customer_id, :department_id => department_id, :user_id => user_id
end
def can_update_entries(customer_id, department_id, user_id)
can :update, Entry, :customer_id => customer_id, :department_id => department_id, :user_id => user_id
end
def can_destroy_entries(customer_id, department_id)
can :destroy, Entry, :customer_id => customer_id, :department_id => department_id
end
...
end
user_ability.rb
class UserAbility < AbilityBase
def initialize(current_user)
if current_user
user_department_type_names = {}
@customer = current_user.customer
@user_type = current_user.user_type
current_user_dept = current_user.departments
@user_department_ids = current_user_dept.collect(&:id)
@user_department_type_ids = current_user_dept.collect { |dept|
dept_type = dept.department_type
user_department_type_names["#{dept_type.type_name}"] = dept.id
dept_type.id
}
...
if user_department_type_names.has_key?("FRONT_OFFICE")
dept_id = user_department_type_names["FRONT_OFFICE"]
if @user_type == "NORMAL_USER"
can_read_entries(customer.id, dept_id)
can_create_entries(customer.id, dept_id, user_id)
can_update_entries(customer.id, dept_id, user_id)
elsif @user_type == "ADMIN"
can_read_entries(customer.id, dept_id)
can_create_entries(customer.id, dept_id, user_id)
can_update_entries(customer.id, dept_id, user_id)
can_destroy_entries(customer.id, dept_id)
end
elsif user_department_type_names.has_key?("BACK_OFFICE")
dept_id = user_department_type_names["BACK_OFFICE"]
if @user_type == "NORMAL_USER"
can_read_entries(customer.id, dept_id)
can_create_entries(customer.id, dept_id, user_id)
can_update_entries(customer.id, dept_id, user_id)
elsif @user_type == "ADMIN"
can_read_entries(customer.id, dept_id)
can_create_entries(customer.id, dept_id, user_id)
can_update_entries(customer.id, dept_id, user_id)
can_destroy_entries(customer.id, dept_id)
end
elsif user_department_type_names.has_key?("ADMIN")
dept_id = user_department_type_names["ADMIN"]
if @user_type == "NORMAL_USER"
can_read_entries(customer.id, dept_id)
can_create_entries(customer.id, dept_id, user_id)
can_update_entries(customer.id, dept_id, user_id)
elsif @user_type == "ADMIN"
can_read_entries(customer.id, dept_id)
can_create_entries(customer.id, dept_id, user_id)
can_update_entries(customer.id, dept_id, user_id)
can_destroy_entries(customer.id, dept_id)
end
end
...
end
end
end
答案
我用有点不同的方法对这样的:
class UserAbility
include CanCan::Ability
attr_accessor :user
def initialize(user)
@user = user
can :read, Entry, do |entry|
is_admin || (is_normal_user && Entry.where(id, entry.id, customer_id: @user.customer_id, dept_id: user.departments.ids).exists?
end
private
def is_normal_user
user.user_type == 'NORMAL_USER'.freeze
end
def is_admin
user.user_type == 'ADMIN'.freeze
end
end
当然这只是一个模板
以上是关于Rails的基于部门CanCanCan资源的能力的主要内容,如果未能解决你的问题,请参考以下文章
Rails 设计角色模型和 CanCanCan - 定义能力
Rails、Devise、Role Model 和 CanCanCan - 定义能力