Add YARD docs for remaining methods

Closes #266
This commit is contained in:
Jonas Nicklas 2016-01-14 16:01:56 +01:00
parent cdeb0fde8f
commit 9855bdf97a
3 changed files with 119 additions and 6 deletions

1
.yardopts Normal file
View File

@ -0,0 +1 @@
--api public --hide-void-return --markup markdown

View File

@ -6,10 +6,17 @@ require "active_support/core_ext/object/blank"
require "active_support/core_ext/module/introspection" require "active_support/core_ext/module/introspection"
require "active_support/dependencies/autoload" require "active_support/dependencies/autoload"
# @api public
module Pundit module Pundit
SUFFIX = "Policy" SUFFIX = "Policy"
# @api private
module Generators; end
# @api private
class Error < StandardError; end class Error < StandardError; end
# Error that will be raiser when authorization has failed
class NotAuthorizedError < Error class NotAuthorizedError < Error
attr_reader :query, :record, :policy attr_reader :query, :record, :policy
@ -27,13 +34,30 @@ module Pundit
super(message) super(message)
end end
end end
# Error that will be raised if a controller action has not called the
# `authorize` or `skip_authorization` methods.
class AuthorizationNotPerformedError < Error; end class AuthorizationNotPerformedError < Error; end
# Error that will be raised if a controller action has not called the
# `policy_scope` or `skip_policy_scope` methods.
class PolicyScopingNotPerformedError < AuthorizationNotPerformedError; end class PolicyScopingNotPerformedError < AuthorizationNotPerformedError; end
# Error that will be raised if a policy or policy scope is not defined.
class NotDefinedError < Error; end class NotDefinedError < Error; end
extend ActiveSupport::Concern extend ActiveSupport::Concern
class << self class << self
# Retrieves the policy for the given record, initializing it with the
# record and user and finally throwing an error if the user is not
# authorized to perform the given action.
#
# @param user [Object] the user that initiated the action
# @param record [Object] the object we're checking permissions of
# @param record [Symbol] the query method to check on the policy (e.g. `:show?`)
# @raise [NotAuthorizedError] if the given query method returned false
# @return [true] Always returns true
def authorize(user, record, query) def authorize(user, record, query)
policy = policy!(user, record) policy = policy!(user, record)
@ -44,25 +68,52 @@ module Pundit
true true
end end
# Retrieves the policy scope for the given record.
#
# @see https://github.com/elabs/pundit#scopes
# @param user [Object] the user that initiated the action
# @param record [Object] the object we're retrieving the policy scope for
# @return [Scope{#resolve}, nil] instance of scope class which can resolve to a scope
def policy_scope(user, scope) def policy_scope(user, scope)
policy_scope = PolicyFinder.new(scope).scope policy_scope = PolicyFinder.new(scope).scope
policy_scope.new(user, scope).resolve if policy_scope policy_scope.new(user, scope).resolve if policy_scope
end end
# Retrieves the policy scope for the given record.
#
# @see https://github.com/elabs/pundit#scopes
# @param user [Object] the user that initiated the action
# @param record [Object] the object we're retrieving the policy scope for
# @raise [NotDefinedError] if the policy scope cannot be found
# @return [Scope{#resolve}] instance of scope class which can resolve to a scope
def policy_scope!(user, scope) def policy_scope!(user, scope)
PolicyFinder.new(scope).scope!.new(user, scope).resolve PolicyFinder.new(scope).scope!.new(user, scope).resolve
end end
# Retrieves the policy for the given record.
#
# @see https://github.com/elabs/pundit#policies
# @param user [Object] the user that initiated the action
# @param record [Object] the object we're retrieving the policy for
# @return [Object, nil] instance of policy class with query methods
def policy(user, record) def policy(user, record)
policy = PolicyFinder.new(record).policy policy = PolicyFinder.new(record).policy
policy.new(user, record) if policy policy.new(user, record) if policy
end end
# Retrieves the policy for the given record.
#
# @see https://github.com/elabs/pundit#policies
# @param user [Object] the user that initiated the action
# @param record [Object] the object we're retrieving the policy for
# @raise [NotDefinedError] if the policy cannot be found
# @return [Object] instance of policy class with query methods
def policy!(user, record) def policy!(user, record)
PolicyFinder.new(record).policy!.new(user, record) PolicyFinder.new(record).policy!.new(user, record)
end end
end end
# @api private
module Helper module Helper
def policy_scope(scope) def policy_scope(scope)
pundit_policy_scope(scope) pundit_policy_scope(scope)
@ -93,22 +144,48 @@ module Pundit
end end
end end
# @return [Boolean] whether authorization has been performed, i.e. whether
# one {#authorize} or {#skip_authorization} has been called
def pundit_policy_authorized? def pundit_policy_authorized?
!!@_pundit_policy_authorized !!@_pundit_policy_authorized
end end
# @return [Boolean] whether policy scoping has been performed, i.e. whether
# one {#policy_scope} or {#skip_policy_scope} has been called
def pundit_policy_scoped? def pundit_policy_scoped?
!!@_pundit_policy_scoped !!@_pundit_policy_scoped
end end
# Raises an error if authorization has not been performed, usually used as an
# `after_action` filter to prevent programmer error in forgetting to call
# {#authorize} or {#skip_authorization}.
#
# @see https://github.com/elabs/pundit#ensuring-policies-are-used
# @raise [AuthorizationNotPerformedError] if authorization has not been performed
# @return [void]
def verify_authorized def verify_authorized
raise AuthorizationNotPerformedError, self.class unless pundit_policy_authorized? raise AuthorizationNotPerformedError, self.class unless pundit_policy_authorized?
end end
# Raises an error if policy scoping has not been performed, usually used as an
# `after_action` filter to prevent programmer error in forgetting to call
# {#policy_scope} or {#skip_policy_scope} in index actions.
#
# @see https://github.com/elabs/pundit#ensuring-policies-are-used
# @raise [AuthorizationNotPerformedError] if policy scoping has not been performed
# @return [void]
def verify_policy_scoped def verify_policy_scoped
raise PolicyScopingNotPerformedError, self.class unless pundit_policy_scoped? raise PolicyScopingNotPerformedError, self.class unless pundit_policy_scoped?
end end
# Retrieves the policy for the given record, initializing it with the record
# and current user and finally throwing an error if the user is not
# authorized to perform the given action.
#
# @param record [Object] the object we're checking permissions of
# @param record [Symbol, nil] the query method to check on the policy (e.g. `:show?`)
# @raise [NotAuthorizedError] if the given query method returned false
# @return [true] Always returns true
def authorize(record, query = nil) def authorize(record, query = nil)
query ||= params[:action].to_s + "?" query ||= params[:action].to_s + "?"
@ -123,23 +200,50 @@ module Pundit
true true
end end
# Allow this action not to perform authorization.
#
# @see https://github.com/elabs/pundit#ensuring-policies-are-used
# @return [void]
def skip_authorization def skip_authorization
@_pundit_policy_authorized = true @_pundit_policy_authorized = true
end end
# Allow this action not to perform policy scoping.
#
# @see https://github.com/elabs/pundit#ensuring-policies-are-used
# @return [void]
def skip_policy_scope def skip_policy_scope
@_pundit_policy_scoped = true @_pundit_policy_scoped = true
end end
# Retrieves the policy scope for the given record.
#
# @see https://github.com/elabs/pundit#scopes
# @param record [Object] the object we're retrieving the policy scope for
# @return [Scope{#resolve}, nil] instance of scope class which can resolve to a scope
def policy_scope(scope) def policy_scope(scope)
@_pundit_policy_scoped = true @_pundit_policy_scoped = true
pundit_policy_scope(scope) pundit_policy_scope(scope)
end end
# Retrieves the policy for the given record.
#
# @see https://github.com/elabs/pundit#policies
# @param record [Object] the object we're retrieving the policy for
# @return [Object, nil] instance of policy class with query methods
def policy(record) def policy(record)
policies[record] ||= Pundit.policy!(pundit_user, record) policies[record] ||= Pundit.policy!(pundit_user, record)
end end
# Retrieves a set of permitted attributes from the policy by instantiating
# the policy class for the given record and calling `permitted_attributes` on
# it, or `permitted_attributes_for_{action}` if it is defined. It then infers
# what key the record should have in the params hash and retrieves the
# permitted attributes from the params hash under that key.
#
# @see https://github.com/elabs/pundit#strong-parameters
# @param record [Object] the object we're retrieving permitted attributes for
# @return [Hash{String => Object}] the permitted attributes
def permitted_attributes(record, action = params[:action]) def permitted_attributes(record, action = params[:action])
param_key = PolicyFinder.new(record).param_key param_key = PolicyFinder.new(record).param_key
policy = policy(record) policy = policy(record)
@ -151,14 +255,25 @@ module Pundit
params.require(param_key).permit(policy.public_send(method_name)) params.require(param_key).permit(policy.public_send(method_name))
end end
# Cache of policies. You should not rely on this method.
#
# @api private
def policies def policies
@_pundit_policies ||= {} @_pundit_policies ||= {}
end end
# Cache of policy scope. You should not rely on this method.
#
# @api private
def policy_scopes def policy_scopes
@_pundit_policy_scopes ||= {} @_pundit_policy_scopes ||= {}
end end
# Hook method which allows customizing which user is passed to policies and
# scopes initialized by {#authorize}, {#policy} and {#policy_scope}.
#
# @see https://github.com/elabs/pundit#customize-pundit-user
# @return [Object] the user object to be used with pundit
def pundit_user def pundit_user
current_user current_user
end end

View File

@ -10,13 +10,13 @@ module Pundit
class PolicyFinder class PolicyFinder
attr_reader :object attr_reader :object
# @param object [any] # @param object [any] the object to find policy and scope classes for
# #
def initialize(object) def initialize(object)
@object = object @object = object
end end
# @return [nil, Scope{#resolve}] # @return [nil, Scope{#resolve}] scope class which can resolve to a scope
# @see https://github.com/elabs/pundit#scopes # @see https://github.com/elabs/pundit#scopes
# @example # @example
# scope = finder.scope #=> UserPolicy::Scope # scope = finder.scope #=> UserPolicy::Scope
@ -43,7 +43,7 @@ module Pundit
nil nil
end end
# @return [Scope{#resolve}] # @return [Scope{#resolve}] scope class which can resolve to a scope
# @raise [NotDefinedError] if scope could not be determined # @raise [NotDefinedError] if scope could not be determined
# #
def scope! def scope!
@ -73,9 +73,6 @@ module Pundit
private private
# @return [String] policy class name
# @api public
#
def find def find
if object.nil? if object.nil?
nil nil