Hi all,
I want to limit access to model objects based on the role of the logged
in
user. It seemed the most blunt way of doing this would be make copies of
each controller which accessed the models and use one of the access
control
systems out there to limit access to the controllers. However, with 9
different controllers this seems like a terrible choice.
Here’s what I’ve come up with. Each controller implements something like
the
following code. Basically, there’s a set_x_with_scope method which
takes
normal find() parameters, then passes them to X.find within
X.with_scope.
So, instead of having @category = Category.find(param[:id]), which would
occur multiple times in the controller, I use
set_category_with_scope(params[:id]), which sets @category and only
allows
access to data based on attributes of the current user.
Right now, I use a collection of methods to build the options for :find
in
with_scope. Soon, I’m going to alter the methods so that their return
values
will depend on the user’s role. I hope all this make sense
On top of all this, I’m using Ezra’s access control plugin to limit
access
to the controllers.
So my question is: is there a better way to do this?
class CategoriesController < ApplicationController
access_control :DEFAULT => ‘(Administrator | SuperUser)’
def edit
set_category_with_scope(params[:id])
end
def update
set_category_with_scope(params[:id])
@category.update_attributes(params[:category])
end
def set_category_with_scope(*args)
Category.with_scope(:find => scoped_options) do
@category = Category.find(*args)
end
end
def scoped_finder_conditions
@scoped_finder_conditions ||= {:conditions => “positions.company_id =
#{current_user.company_id}”}
end
def scoped_finder_include
@scoped_finder_include ||= {:include => :position}
end
def scoped_options
scoped_finder_conditions.merge(scoped_finder_include)
end
Thanks!
Daniel