I'm relying on ActiveSupport::Concern
to simplify the module. I store my concerns in a directory called concerns
under app
. I've called this one inherited_resources_with_authority.rb
and you may need to modify your autoload_paths
in application.rb
to load files from this folder.
module InheritedResourcesWithAuthority
extend ActiveSupport::Concern
included do
inherit_resources
authorize_actions_for :resource_class
alias_method_chain :resource, :authority
alias_method_chain :build_resource, :authority
alias_method_chain :update_resource, :authority
end
protected
def resource_with_authority
resource_without_authority
authorize_action_for(get_resource_ivar)
end
def build_resource_with_authority
build_resource_without_authority
authorize_action_for(get_resource_ivar)
end
def update_resource_with_authority(object, attributes)
object.assign_attributes(*attributes)
authorize_action_for(object)
object.save
end
end
We're basically chaining important inherited_resources
' abstract methods and inserting our authorisation code where necessary. The last one is the trickiest as we can't call the original method that we're chaining on to so we have to duplicate some of inherited_resources
' code here.
To use this concern simply call include InheritedResourcesWithAuthority
from your controller.
Note that you must not use the class inheritance method of activating inherited_resources
on your controller as we're already using the other method in this concern.
Full writeup here: https://coderwall.com/p/tp5sig
Suggestions are definitely welcome :D