Created
July 3, 2012 18:56
-
-
Save tvdeyen/3041942 to your computer and use it in GitHub Desktop.
Spree tax calculation patch
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
StateMachine::Machine.ignore_method_conflicts = true | |
module Spree | |
Order.class_eval do | |
# customize the checkout state machine | |
Order.state_machines[:state] = StateMachine::Machine.new(Order, :initial => 'cart') do | |
event :next do | |
transition :from => 'cart', :to => 'address' | |
transition :from => 'address', :to => 'delivery' | |
transition :from => 'delivery', :to => 'payment', :if => :payment_required? | |
transition :from => 'delivery', :to => 'confirm' | |
transition :from => 'payment', :to => 'confirm' | |
transition :from => 'confirm', :to => 'complete' | |
end | |
event :cancel do | |
transition :to => 'canceled', :if => :allow_cancel? | |
end | |
event :return do | |
transition :to => 'returned', :from => 'awaiting_return' | |
end | |
event :resume do | |
transition :to => 'resumed', :from => 'canceled', :if => :allow_resume? | |
end | |
event :authorize_return do | |
transition :to => 'awaiting_return' | |
end | |
before_transition :to => 'complete' do |order| | |
begin | |
order.process_payments! | |
rescue Core::GatewayError | |
if Spree::Config[:allow_checkout_on_gateway_error] | |
true | |
else | |
false | |
end | |
end | |
end | |
before_transition :to => ['delivery'] do |order| | |
order.shipments.each { |s| s.destroy unless s.shipping_method.available_to_order?(order) } | |
end | |
# updating tax because of promotions | |
before_transition :to => 'confirm', :do => :create_tax_charge! | |
after_transition :to => 'complete', :do => :finalize! | |
after_transition :to => 'delivery', :do => :create_tax_charge! | |
after_transition :to => 'payment', :do => :create_shipment! | |
after_transition :to => 'resumed', :do => :after_resume | |
after_transition :to => 'canceled', :do => :after_cancel | |
end | |
# Updates the following Order total values: | |
# | |
# +payment_total+ The total value of all finalized Payments (NOTE: non-finalized Payments are excluded) | |
# +item_total+ The total value of all LineItems | |
# +adjustment_total+ The total value of all adjustments (promotions, credits, etc.) | |
# +total+ The so-called "order total." This is equivalent to +item_total+ plus +adjustment_total+. | |
def update_totals | |
# update_adjustments | |
self.payment_total = payments.completed.map(&:amount).sum | |
self.item_total = line_items.map(&:amount).sum | |
# Only use shipping and promotions for adjustment | |
self.adjustment_total = adjustments.shipping.eligible.map(&:amount).sum | |
self.adjustment_total += adjustments.promotion.eligible.map(&:amount).sum | |
self.total = item_total + adjustment_total | |
end | |
end | |
end |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
module Spree | |
TaxRate.class_eval do | |
# Creates necessary tax adjustments for the order. | |
def adjust(order) | |
label = "#{tax_category.name} #{amount * 100}%" | |
if self.included_in_price | |
if Zone.default_tax.contains? order.tax_zone | |
amount = 0 | |
order.line_items.each do |line_item| | |
amount += calculator.compute(line_item) | |
end | |
if order.adjustments.promotion.eligible.any? | |
factor = order.adjustments.promotion.eligible.map(&:amount).sum.abs / order.item_total | |
amount = amount - ( amount * factor ) | |
amount = BigDecimal.new(amount.to_s).round(2, BigDecimal::ROUND_HALF_UP) | |
end | |
return if amount == 0 | |
order.adjustments.create(:amount => amount, | |
:source => order, | |
:originator => self, | |
:locked => true, | |
:label => label) | |
else | |
amount = -1 * calculator.compute(order) | |
label = I18n.t(:refund) + label | |
order.adjustments.create(:amount => amount, | |
:source => order, | |
:originator => self, | |
:locked => true, | |
:label => label) | |
end | |
else | |
create_adjustment(label, order, order) | |
end | |
end | |
end | |
end |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment