Class: Coupon::Calculator::PercentageOffPerQtyMet

Inherits:
Base
  • Object
show all
Defined in:
app/services/coupon/calculator/percentage_off_per_qty_met.rb

Overview

Classic percentage off calculator, applies the percentage_off
specified in the initialization options to each qualifying products
in the line item extractor
line_item_extractor: an instance of ProductFilter::LineExtractor
tax_class: :g, :svc, :shp
options:
:percentage_off (required), the percentage to apply, e.g. 0.02 for 2%

Instance Attribute Summary collapse

Instance Method Summary collapse

Constructor Details

#initialize(line_item_extractor, percentage_off:, msrp: false) ⇒ PercentageOffPerQtyMet

Returns a new instance of PercentageOffPerQtyMet.



13
14
15
16
17
# File 'app/services/coupon/calculator/percentage_off_per_qty_met.rb', line 13

def initialize(line_item_extractor, percentage_off:, msrp: false)
  @percentage_off = percentage_off
  @msrp = msrp
  super # passes the arguments as they came
end

Instance Attribute Details

#msrpObject (readonly)

Returns the value of attribute msrp.



11
12
13
# File 'app/services/coupon/calculator/percentage_off_per_qty_met.rb', line 11

def msrp
  @msrp
end

#percentage_offObject (readonly)

Returns the value of attribute percentage_off.



11
12
13
# File 'app/services/coupon/calculator/percentage_off_per_qty_met.rb', line 11

def percentage_off
  @percentage_off
end

Instance Method Details

#calculate(discount) ⇒ Object



19
20
21
22
23
24
25
26
27
28
29
30
31
32
# File 'app/services/coupon/calculator/percentage_off_per_qty_met.rb', line 19

def calculate(discount)
  qty_min_repeat = line_item_extractor.qty_min_repeat
  return unless qty_min_repeat > 0

  line_item_extractor.discountable_line_items.each do |line_item|
    # Skip lines with zero quantity to avoid division by zero (produces Infinity)
    next if line_item.quantity.zero?

    base_amount = msrp ? line_item.price : line_item.discounted_price
    allocated_unit_amount = -(base_amount * percentage_off).ceil(2)
    allocated_unit_amount = allocated_unit_amount * qty_min_repeat / line_item.quantity
    allocate_to_line(line_item, discount, allocated_unit_amount)
  end
end