Context aware authorization using CanCan

点点圈 提交于 2019-12-02 21:13:20
Max

Ok, I solved the problem. My use case is briefly mentioned in the beginning of the CanCan README and I missed it. You can define new Ability classes in app/models/ that take in a different parameter other than current_user. To do so, you put the following in your controller:

def current_ability 
  if params[:controller] == 'leagues'
    @current_ability = LeagueAbility.new(current_user_league_relation)
  elsif params[:controller] == 'league_relations'
    @current_ability = LeagueRelationAbility.new(current_user_league_relation)
  else
    @current_ability = Ability.new(current_user)
  end
end

Now you can create league_ability.rb in app/models/.

class LeagueAbility
  include CanCan::Ability

  def initialize(league_relation)
    league_relation ||= LeagueRelation.new

    if league_relation.owner?
      can :manage, League, :id => league_relation.league_id
    elsif league_relation.moderator?
      can :manage, League, :id => league_relation.league_id
      cannot [:delete, :destroy], League
    else
      can :read, League
      can :create, League
    end    
  end
end

One thing to note is that this relies on your application controller calling a method in a child class. Hope that helps!

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!