views:

373

answers:

2

I'm following Ryan Bates' declarative authorization railscast. I'm trying to add functionality for author of a particular article to be able to edit comments left in his article, regardless of if he is the owner or not. I tried doing it, but couldn't get it to work.

  role :author do
    has_permission_on :articles, :to => [:new, :create]
    has_permission_on :articles, :to => [:edit, :update, :show] do
      if_attribute :user => is { user }
    end
    **has_permission_on :comments, :to => [:edit, :update] do
      if_attribute :article_id => is { user }
    end**
  end

How do I modify the has_permission on comments line to allow user to edit comments if they are left in his article only?

Thanks

A: 

Your first declaration...

has_permission_on :articles, :to => [:edit, :update, :show] do
  if_attribute :user => is { user }
end

... perfectly works, because if :user is equal to user (which is the current logged in user - current_user) you have permission to do the declared actions on :articles.

But if you look at the second one...

has_permission_on :comments, :to => [:edit, :update] do
  if_attribute :article_id => is { user }
end

you can see that the attribute :article_id is never going to be equal to the current logged in user.

Now I'm a Rails newbie myself and I just used some basic functionality of declarative authorization, so I don't know the exact answer to your problem. But I think you must find a way to access the articles of that user, something like if_attribute :article_id => is { user.articles.id }.

Maybe you can find an answer here in the documentation

jd291
Yea I tried doing that without any help. I guess I'll need to pass in some additional parameters.
Senthil
+3  A: 

Hello

In order to allow a user to edit the comments that are published in his/her articles, the rule should looks like:

role :author do
  [...]

  has_permission_on :comments, :to => [:edit, :update] do
    if_attribute :article_id => is_in { user.article_ids }
  end
end

Please, notice the change of is by is_in

Optionally, you may change the user.article_ids by user.articles.collect{|a| a.id}.uniq

fjuan
Ah I didn't even think of using user.article_ids. Thanks that works.
Senthil