yerassyl
yerassyl

Reputation: 3057

Role inheritance in cancancan with hash conditions

I am doing Rails 4.2 app with CanCanCan gem. I have my ability.rb class. I am doing separate role model as explained in gem docs and a role inheritance as explained too.

class Ability
  include CanCan::Ability

  def initialize(user)
      user ||= User.new # guest user (not logged in)
      user.roles.each { |role| send(role.name.downcase) }

  end

  # write down role permissions here

  def client
    can :manage, Client, :id => user.id
    can [:read,:create], Patient
  end

end

Basically each role is a method which gets called I suppose in user.role.each block. I do not understand fully what it does. What i need is to be able access user variable inside role methods as in def client example. Is making user global a solution. Or are there any good solutions?

Upvotes: 1

Views: 531

Answers (2)

yerassyl
yerassyl

Reputation: 3057

Ok I solved my problem this way. I added user as a parameter to send:

user.roles.each { |role| send(role.name.downcase, user) }

and added method:

#ability.rb
def any_patient?(client, id)
    client.patients.any? {|p| p.id == id }
end

And then I do:

def client(user)
    can [:read], Patient do |patient|
      any_patient?(user.client, patient.id)
    end

  end

So I am telling that client can read any patient that he owns.

Upvotes: 0

Richard Peck
Richard Peck

Reputation: 76784

Simplest way...

#app/models/ability.rb
class Ability
  include CanCan::Ability

  def initialize(user)
      user ||= User.new # guest user (not logged in)
      if user.role == "client"
         can :manage, Client, :id => user.id
         can [:read,:create], Patient
      elsif user.role == "x"
         ...
      end    
  end
end

You can read more here.

Upvotes: 0

Related Questions