app/controllers/active_admin/base_controller/authorization.rb
# frozen_string_literal: true
module ActiveAdmin
class BaseController < ::InheritedResources::Base
module Authorization
extend ActiveSupport::Concern
ACTIONS_DICTIONARY = {
index: ActiveAdmin::Authorization::READ,
show: ActiveAdmin::Authorization::READ,
new: ActiveAdmin::Authorization::NEW,
create: ActiveAdmin::Authorization::CREATE,
edit: ActiveAdmin::Authorization::EDIT,
update: ActiveAdmin::Authorization::UPDATE,
destroy: ActiveAdmin::Authorization::DESTROY
}
included do
rescue_from ActiveAdmin::AccessDenied, with: :dispatch_active_admin_access_denied
helper_method :authorized?
helper_method :authorize!
helper_method :active_admin_authorization
end
protected
# Authorize the action and subject. Available in the controller
# as well as all the views.
#
# @param [Symbol] action The action to check if the user has permission
# to perform on the subject.
#
# @param [any] subject The subject that the user is trying to perform
# the action on.
#
# @return [Boolean]
#
def authorized?(action, subject = nil)
active_admin_authorization.authorized?(action, subject)
end
# Authorize the action and subject. Available in the controller
# as well as all the views. If the action is not allowed, it raises
# an ActiveAdmin::AccessDenied exception.
#
# @param [Symbol] action The action to check if the user has permission
# to perform on the subject.
#
# @param [any] subject The subject that the user is trying to perform
# the action on.
#
# @return [Boolean] True if authorized, otherwise raises
# an ActiveAdmin::AccessDenied.
def authorize!(action, subject = nil)
unless authorized? action, subject
raise ActiveAdmin::AccessDenied.new(
current_active_admin_user,
action,
subject)
end
end
# Performs authorization on the resource using the current controller
# action as the permission action.
#
def authorize_resource!(resource)
permission = action_to_permission(params[:action])
authorize! permission, resource
end
# Retrieve or instantiate the authorization instance for this resource
#
# @return [ActiveAdmin::AuthorizationAdapter]
def active_admin_authorization
@active_admin_authorization ||=
active_admin_authorization_adapter.new active_admin_config, current_active_admin_user
end
# Returns the class to be used as the authorization adapter
#
# @return [Class]
def active_admin_authorization_adapter
adapter = active_admin_namespace.authorization_adapter
if adapter.is_a? String
adapter.constantize
else
adapter
end
end
# Converts a controller action into one of the correct Active Admin
# authorization names. Uses the ACTIONS_DICTIONARY to convert the
# action name to permission.
#
# @param [String, Symbol] action The controller action name.
#
# @return [Symbol] The permission name to use.
def action_to_permission(action)
if action && action = action.to_sym
Authorization::ACTIONS_DICTIONARY[action] || action
end
end
def dispatch_active_admin_access_denied(exception)
instance_exec(self, exception, &active_admin_namespace.on_unauthorized_access.to_proc)
end
def rescue_active_admin_access_denied(exception)
error = exception.message
respond_to do |format|
format.html do
flash[:error] = error
redirect_backwards_or_to_root
end
format.csv { render body: error, status: :unauthorized }
format.json { render json: { error: error }, status: :unauthorized }
format.xml { render xml: "<error>#{error}</error>", status: :unauthorized }
end
end
def redirect_backwards_or_to_root
redirect_back fallback_location: active_admin_root
end
end
end
end