lib/eco/api/session/batch/base_policy.rb in eco-helpers-1.1.8 vs lib/eco/api/session/batch/base_policy.rb in eco-helpers-1.2.1
- old
+ new
@@ -17,90 +17,36 @@
#
# @attr_reader attr [Symbol] the Symbol `name` of the current policy
# @attr_reader max [Integer] `max` **allowed** number of occurrences of the property
# @attr_reader min [Integer] `min` **required** number of occurrences of the property
class BasePolicy
- extend Eco::API::Common::ClassHelpers
+ extend Eco::API::Common::ClassHierarchy
- # @attr_reader model [Hash, nil] the `model` of the current `class`
class << self
- attr_reader :model
- # @param value [Hash, Enumerable, String, Symbol, nil] unparsed model to be assigned to the `class`
- def model=(value)
- @model = parse_model(value)
- end
-
- # @return [Array<String>] the `keys` of the current class' `model`
- def model_attrs
- (model && model.keys) || []
- end
-
- # Helper to normalize `key` into a correct `ruby` **constant name**
- # @param key [String, Symbol] to be normalized
- # @return [String] a correct constant name
- def titleize(key)
- str_name = key.to_s.strip.split(/[\-\_ ]/i).compact.map do |str|
- str.slice(0).upcase + str.slice(1..-1).downcase
- end.join("")
- end
-
# If the class for `key` exists, it returns it. Otherwise it generates it.
# @note for this to work, `key` should be one of the submodels of the current class' `model`
# @return [Eco::API::Session::Batch::BasePolicy] or subclass thereof
def policy_class(key)
key = key.to_sym.freeze
- class_name = titleize(key)
- full_class_name = "#{self}::#{class_name}"
+ class_name = to_constant(key)
- unless target_class = resolve_class(full_class_name, exception: false)
- submodel = model[key]
- target_class = Class.new(self) do |klass|
- klass.model = submodel
- policy_attrs *klass.model_attrs
- end
-
- self.const_set class_name, target_class
+ new_class(class_name, inherits: Eco::API::Session::Batch::BasePolicy) do |klass|
+ klass.model = model[key]
+ klass.policy_attrs *klass.model_attrs
end
-
- target_class
end
- # Thanks to this step the format on the declaration of the model is flexible
- # @param value [Hash, Enumerable, String, Symbol, nil]
- # @return [Hash, nil] where keys are `Symbol` s
- def parse_model(model)
- case model
- when String
- return parse_model(model.to_sym)
- when Symbol
- return {model => nil}
- when Hash
- return model.each_with_object({}) do |(k,v), hash|
- hash[k.to_sym] = v
- end
- when Enumerable
- return model.each_with_object({}) do |sub, hash|
- hash.merge!(parse_model(sub))
- end
- when NilClass
- return nil
- else
- raise "Incorrect model declaration, allowed String, Symbol, Hash and Enumerable. Given: #{model.class}"
- end
- end
-
# Attributes of this level of the model that should be included
# @param attr [Symbol, String] each of the subpolicies of the model that should be available
def policy_attrs(*attrs)
attrs = attrs.map(&:to_sym)
attrs.each do |attr|
method = attr.to_s.freeze
var = "@#{method}".freeze
define_method(method) do |&block|
-
unless policy = self[attr]
klass = self.class.policy_class(attr)
policy = self[attr] = klass.new(attr, _parent: self)
end