Module: Spree::Core::CalculatedAdjustments

Included in:
Promotion::Actions::CreateAdjustment, ShippingMethod, TaxRate
Defined in:
lib/spree/core/calculated_adjustments.rb

Class Method Summary collapse

Class Method Details

.included(klass) ⇒ Object



4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
# File 'lib/spree/core/calculated_adjustments.rb', line 4

def self.included(klass)
  klass.class_eval do
    has_one   :calculator, :as => :calculable, :dependent => :destroy
    accepts_nested_attributes_for :calculator
    attr_accessible :calculator_type, :calculator_attributes
    validates :calculator, :presence => true

    def self.calculators
      spree_calculators.send model_name_without_spree_namespace
    end

    def calculator_type
      calculator.class.to_s if calculator
    end

    def calculator_type=(calculator_type)
      klass = calculator_type.constantize if calculator_type
      self.calculator = klass.new if klass && !self.calculator.is_a?(klass)
    end

    # Creates a new adjustment for the target object (which is any class that has_many :adjustments) and
    # sets amount based on the calculator as applied to the calculable argument (Order, LineItems[], Shipment, etc.)
    # By default the adjustment will not be considered mandatory
    def create_adjustment(label, target, calculable, mandatory=false, state="closed")
      amount = compute_amount(calculable)
      return if amount == 0 && !mandatory
      target.adjustments.create({ :amount => amount,
                                  :source => calculable,
                                  :originator => self,
                                  :label => label,
                                  :mandatory => mandatory,
                                  :state => state }, :without_protection => true)
    end

    # Updates the amount of the adjustment using our Calculator and calling the +compute+ method with the +calculable+
    # referenced passed to the method.
    def update_adjustment(adjustment, calculable)
      adjustment.update_attribute_without_callbacks(:amount, compute_amount(calculable))
    end

    # Calculate the amount to be used when creating an adjustment
    # NOTE: May be overriden by classes where this module is included into.
    # Such as Spree::Promotion::Action::CreateAdjustment.
    def compute_amount(calculable)
      self.calculator.compute(calculable)
    end

    private
    def self.model_name_without_spree_namespace
      self.to_s.tableize.gsub('/', '_').sub('spree_', '')
    end

    def self.spree_calculators
      Rails.application.config.spree.calculators
    end
  end
end