Search code examples
ruby-on-railsassociationscancan

CanCanCan authorize associated objects


My Routes.rb:

resources :users
resources :clients do
  resources :branches
end

I have this in Ability.rb. User can update only his own clients.

  can [:update], Client, :id => user.clients.pluck(:id)

User should be also able to :create, :update, :show branches which belong to client. It might look somehting like this:

  can [:create, :update, :show], Branch, :client => { :id => user.clients.pluck(:id) }

It works for :update, :show, but not for :create. It's because new Branch doesn't have client_id before create. How do I make it work for :create?


Solution

  • Your current ability is actually not calling a check on the foreign key field on branch. Using nesting like that is calling the equivalent of client.id instead of client_id like you want.

    Should read:

    can [:create, :update, :show], Branch, client_id: user.client_ids

    or, staying consistent with your style:

    can [:create, :update, :show], Branch, client_id: user.clients.pluck(:id)