Module: ActionPolicy::Policy::Core
Overview
Core policy API
Defined Under Namespace
Modules: ClassMethods
Instance Attribute Summary collapse
-
#record ⇒ Object
readonly
Returns the value of attribute record.
Class Method Summary collapse
Instance Method Summary collapse
-
#__apply__(rule) ⇒ Object
This method performs the rule call.
- #allow! ⇒ Object
-
#allowed_to?(rule, record = :__undef__, **options) ⇒ Boolean
Returns a result of applying the specified rule to the specified record.
-
#apply(rule) ⇒ Object
Returns a result of applying the specified rule (true of false).
-
#apply_r(rule) ⇒ Object
NEXT_RELEASE: This is gonna be #apply in 1.0.
-
#check?(*args, **hargs) ⇒ Boolean
An alias for readability purposes.
- #deny! ⇒ Object
-
#initialize(record = nil) ⇒ Object
NEXT_RELEASE: deprecate ‘record` arg, migrate to `record: nil`.
-
#inspect_rule(rule) ⇒ Object
Return annotated source code for the rule NOTE: require “method_source” and “prism” gems to be installed.
-
#pp(rule) ⇒ Object
Helper for printing the annotated rule source.
-
#resolve_rule(activity) ⇒ Object
Returns a rule name (policy method name) for activity.
-
#result ⇒ Object
Returns the result object for the last rule application within the given execution context (Thread or Fiber).
-
#with_result(rule) ⇒ Object
Prepare a new result object for the next rule application.
Methods included from Behaviours::PolicyFor
#authorization_context, #authorization_namespace, #authorization_strict_namespace, #build_authorization_context, #default_authorization_policy_class, #implicit_authorization_target, #implicit_authorization_target!, #policy_for, #policy_for_cache_key
Instance Attribute Details
#record ⇒ Object (readonly)
Returns the value of attribute record.
75 76 77 |
# File 'lib/action_policy/policy/core.rb', line 75 def record @record end |
Class Method Details
.included(base) ⇒ Object
43 44 45 46 47 48 49 50 51 52 53 54 55 |
# File 'lib/action_policy/policy/core.rb', line 43 def included(base) base.extend ClassMethods # Generate a new class for each _policy chain_ # in order to extend it independently base.module_eval do @result_class = Class.new(ExecutionResult) # we need to make this class _named_, # 'cause anonymous classes couldn't be marshalled base.const_set(:APR, @result_class) end end |
Instance Method Details
#__apply__(rule) ⇒ Object
This method performs the rule call. Override or extend it to provide custom functionality (such as caching, pre checks, etc.)
118 |
# File 'lib/action_policy/policy/core.rb', line 118 def __apply__(rule) = public_send(rule) |
#allow! ⇒ Object
110 111 112 113 |
# File 'lib/action_policy/policy/core.rb', line 110 def allow! result&.load true throw :policy_fulfilled end |
#allowed_to?(rule, record = :__undef__, **options) ⇒ Boolean
Returns a result of applying the specified rule to the specified record. Under the hood a policy class for record is resolved (unless it’s explicitly set through ‘with` option).
If record is ‘nil` then we uses the current policy.
138 139 140 141 142 143 144 145 146 |
# File 'lib/action_policy/policy/core.rb', line 138 def allowed_to?(rule, record = :__undef__, **) if (record == :__undef__ || record == self.record) && .empty? __apply__(resolve_rule(rule)) else policy_for(record: record, **).then do |policy| policy.apply(policy.resolve_rule(rule)) end end end |
#apply(rule) ⇒ Object
Returns a result of applying the specified rule (true of false). Unlike simply calling a predicate rule (‘policy.manage?`), `apply` also calls pre-checks.
85 86 87 88 89 90 91 92 |
# File 'lib/action_policy/policy/core.rb', line 85 def apply(rule) res = apply_r(rule) # DEPRECATED (we still rely on it in tests) @result = res res.value end |
#apply_r(rule) ⇒ Object
NEXT_RELEASE: This is gonna be #apply in 1.0
95 96 97 98 99 100 101 102 103 |
# File 'lib/action_policy/policy/core.rb', line 95 def apply_r(rule) # :nodoc: with_result(rule) do |result| catch :policy_fulfilled do result.load __apply__(resolve_rule(rule)) end result end end |
#check?(*args, **hargs) ⇒ Boolean
An alias for readability purposes
149 |
# File 'lib/action_policy/policy/core.rb', line 149 def check?(*args, **hargs) = allowed_to?(*args, **hargs) |
#deny! ⇒ Object
105 106 107 108 |
# File 'lib/action_policy/policy/core.rb', line 105 def deny! result&.load false throw :policy_fulfilled end |
#initialize(record = nil) ⇒ Object
NEXT_RELEASE: deprecate ‘record` arg, migrate to `record: nil`
78 79 80 |
# File 'lib/action_policy/policy/core.rb', line 78 def initialize(record = nil, *) @record = record end |
#inspect_rule(rule) ⇒ Object
Return annotated source code for the rule NOTE: require “method_source” and “prism” gems to be installed. Otherwise returns empty string.
172 |
# File 'lib/action_policy/policy/core.rb', line 172 def inspect_rule(rule) = PrettyPrint.print_method(self, rule) |
#pp(rule) ⇒ Object
Helper for printing the annotated rule source. Useful for debugging: type ‘pp :show?` within the context of the policy to preview the rule.
177 178 179 180 181 182 183 |
# File 'lib/action_policy/policy/core.rb', line 177 def pp(rule) with_result(rule) do header = "#{self.class.name}##{rule}" source = inspect_rule(rule) $stdout.puts "#{header}\n#{source}" end end |
#resolve_rule(activity) ⇒ Object
Returns a rule name (policy method name) for activity.
By default, rule name is equal to activity name.
Raises ActionPolicy::UnknownRule when rule is not found in policy.
156 157 158 159 160 |
# File 'lib/action_policy/policy/core.rb', line 156 def resolve_rule(activity) raise UnknownRule.new(self, activity) unless respond_to?(activity) activity end |
#result ⇒ Object
Returns the result object for the last rule application within the given execution context (Thread or Fiber)
164 165 166 167 |
# File 'lib/action_policy/policy/core.rb', line 164 def result # FIXME: Remove ivar fallback after 1.0 Thread.current[:__action_policy_result__]&.last || @result end |
#with_result(rule) ⇒ Object
Prepare a new result object for the next rule application. It’s stored in the thread-local storage to be accessible from within the policy.
122 123 124 125 126 127 128 129 130 131 |
# File 'lib/action_policy/policy/core.rb', line 122 def with_result(rule) # :nodoc: result = self.class.result_class.new(self.class, rule) Thread.current[:__action_policy_result__] ||= [] Thread.current[:__action_policy_result__] << result yield result ensure Thread.current[:__action_policy_result__]&.pop end |