ActiveRecord 3.1 - Mass-Assignment Roles

62 views
Skip to first unread message

Pan Thomakos

unread,
May 12, 2011, 8:00:33 PM5/12/11
to rubyonra...@googlegroups.com
Hi,

I think it's awesome that Rails 3.1 introduces the attribute accessible roles/permissions:

class User
  attr_accessible :name, :as => :admin
end

User.create(params[:user], :as => :admin)

But would it be possible to make this a chained function as was done with find, where and
scopes from Rails 2.x to Rails 3.0? Here's a little more on the topic. Maybe ARel could be
leveraged to do this?

I can see that there might be conflicts with user defined scopes, but isn't chaining functions
just so much more elegant than passing multiple hash parameters to a function?

Thanks,
Pan

Kristian Mandrup

unread,
May 18, 2011, 11:52:15 AM5/18/11
to Ruby on Rails: Core
I'm curious whether you can define the :as option as a list of roles?
All the examples I have seen only has the :as linked to the single
role :admin.
How would I use this with a roles system?

Say I had a #current_user_roles method available from my Controller or
whatever.

def update
Project.update_attributes(params[:project], :as =>
current_user_roles)
end

One possible DSL tweak allow something like this:

as_role current_user_roles do |role|
role.update_attributes_of(Project).with params[:project]
role.create(Project).with params[:project]
end

Here the #as_role should return some object that has the methods
#update_attributes #create and so on and a method/reader for the roles
to apply the role permission check.


On May 13, 2:00 am, Pan Thomakos <pan.thoma...@gmail.com> wrote:
> Hi,
>
> I think it's awesome that Rails 3.1 introduces the attribute accessible
> roles/permissions:
>
> class User
>   attr_accessible :name, :as => :admin
> end
>
> User.create(params[:user], :as => :admin)
>
> But would it be possible to make this a chained function as was done with
> find, where and
> scopes from Rails 2.x to Rails 3.0? Here's a little more on the
> topic<http://ablogaboutcode.com/2011/05/12/activerecord-3-1-mass-assignment...>.

Michael Koziarski

unread,
May 18, 2011, 12:11:17 PM5/18/11
to rubyonra...@googlegroups.com
On Wed, May 18, 2011 at 11:52 AM, Kristian Mandrup <kman...@gmail.com> wrote:
> I'm curious whether you can define the :as option as a list of roles?
> All the examples I have seen only has the :as linked to the single
> role :admin.

In short, no, it's not a 'role' in the sense that you mean here,
rather the name of a parameter filter to use. Your app itself will
need to have it's own logic and semantics for figuring out which
filter to use based on your own business rules.

> --
> You received this message because you are subscribed to the Google Groups "Ruby on Rails: Core" group.
> To post to this group, send email to rubyonra...@googlegroups.com.
> To unsubscribe from this group, send email to rubyonrails-co...@googlegroups.com.
> For more options, visit this group at http://groups.google.com/group/rubyonrails-core?hl=en.
>
>

--
Cheers

Koz

Kristian Mandrup

unread,
May 18, 2011, 2:16:11 PM5/18/11
to Ruby on Rails: Core
I understand that it is just a simple symbol match and you have to
write your own business logic behind it:
If we imagine we have a role system along these lines, where a
#the_current_user method returns a User instance that has a
#roles_list method that returns an array of roles (as Symbols)
Then we could imagine something like the following logic to make it a
bit more convenient and logic DSL like (IMO):

# as_role current_user_roles do |role|
# role.update_attributes_of(Project).with params[:project]
# role.create(Project).with params[:project]
# end
def as_role role, &block
yield RoleModelManager.new role
end

def as_roles *roles, &block
yield RoleModelManager.new roles.flatten
end

class RoleModelManager
attr_accessor :roles

def initialize *roles
@roles = roles.flatten
end

def update_attributes_of model_clazz
AttributesUpdater.new model_clazz
end

def create model_clazz
ModelCreator.new model_clazz
end

class AttributesUpdater
attr_accessor :clazz

def initialize clazz
@clazz = clazz
end

def with attributes = {}
clazz.constantize.update_attributes(attributes.merge(:as =>
roles))
end
end

class ModelCreator
attr_accessor :clazz

def initialize clazz
@clazz = clazz
end

def with attributes = {}
clazz.constantize.create(attributes.merge(:as => roles))
end
end
end

def current_roles
the_current_user.roles_list
end

What do you think? My question is, if the current logic relating to
the :as option can evaluate according to an array of symbols (using
#include? fx) ?

On May 18, 6:11 pm, Michael Koziarski <mich...@koziarski.com> wrote:

Michael Koziarski

unread,
May 18, 2011, 2:25:30 PM5/18/11
to rubyonra...@googlegroups.com
> What do you think? My question is, if the current logic relating to
> the :as option can evaluate according to an array of symbols (using
> #include? fx) ?

What would multiple values mean for :as? Any of these? all of these?
There's no valid / sane semantics for merging black and white lists
together.

You'll probably always have to do that yourself, this isn't intended
for the use case you seem to have.

--
Cheers

Koz

Reply all
Reply to author
Forward
0 new messages