Back

Cancan 的alias action 与 核心方法 can (alias action of Cancan and its core method: can)

发布时间: 2013-01-28 06:02:00

( 从 CanCan::Ability 这个RDOC中拿过来的)( grabbed from its rdoc)

1. 核心方法 can

可以定义 可用的ability. 参数1是 action, 参数2 是对象名 (Defines which abilities are allowed using two arguments. The first one is the action you’re setting the permission for, the second one is the class of object you’re setting it on. )

can :update, Article 

做为懒人,咱也可以传入一个数组: (You can pass an array for either of these parameters to match any one. Here the user has the ability to update or destroy both articles and comments. )

can [:update, :destroy], [Article, Comment] 

:all 代表所有的对象, :manage 代表所有的action( You can pass :all to match any object and :manage to match any action. Here are some examples. )

can :manage, :all
can :update, :all
can :manage, Project

也可以传入一个hash. 下面的例子,是该用户只能read 属于自己的 , active = true的project ( You can pass a hash of conditions as the third argument. Here the user can only see active projects which he owns. )

can :read, Project, :active => true, :user_id => user.id 

更多关于 DB 查询的内容请看 ActiveRecordAdditions#accessible_by 与 ControllerAdditions#load_resource ( See ActiveRecordAdditions#accessible_by for how to use this in database queries. These conditions are also used for initial attributes when building a record in ControllerAdditions#load_resource. )

如果HASH参数不能满足你的要求的话,也可以传入一个block ( If the conditions hash does not give you enough control over defining abilities, you can use a block along with any Ruby code you want. )

can :update, Project do |project|
  project.groups.include?(user.group)
end

If the block returns true then the user has that :update ability for that project, otherwise he will be denied access. The downside to using a block is that it cannot be used to generate conditions for database queries.

也可以指定对某个 object instance 检查ability. 注意,参数是一个symbol ( You can pass custom objects into this “can” method, this is usually done with a symbol and is useful if a class isn’t available to define permissions on. )

can :read, :stats can? :read, :stats # => true

重要: 方法 can? 不会引用 条件参数 hash ( IMPORTANT: Neither a hash of conditions or a block will be used when checking permission on a class. )

can :update, Project, :priority => 3
can? :update, Project # => true

如果你想定制can方法的话,那么就如下所示,仅仅传入一个block . 这个方式在你使用db验证时尤其有效 ( If you pass no arguments to can, the action, class, and object will be passed to the block and the block will always be executed. This allows you to override the full behavior if the permissions are defined in an external source such as the database. )

can do |action, object_class, object|
  # check the database and return true/false
end

2. alias_action :  

可以把 多个action 重命名成1个新的。 (Alias one or more actions into another one. )

alias_action :update, :destroy, :to => :modify
can :modify, Comment
Then :modify permission will apply to both :update and :destroy requests.

can? :update, Comment # => true
can? :destroy, Comment # => true

(看例子吧,文字描述的让我觉得模糊) This only works in one direction. Passing the aliased action into the “can?” call will not work because aliases are meant to generate more generic actions.

alias_action :update, :destroy, :to => :modify
can :update, Comment
can? :modify, Comment # => false
Unless that exact alias is used.
can :modify, Comment
can? :modify, Comment # => true

下面是已经默认使用的 alias_action了。对read, manage 有疑问的同学可以留意一下了。(The following aliases are added by default for conveniently mapping common controller actions. )

alias_action :index, :show, :to => :read
# wrong: alias_action :new, :create, :to => :create
alias_action :new, :to => :create  
alias_action :edit, :to => :update

Back