I'm not able to auto-capture a payment in spree. I've tried that (by setting auto-capture option to true in admin panel) with PaymentMethod::Check method and my custom method but it always leaves payment method at pending state. My custom method is based on the PaymentMethod::Check source code and looks like that:
module Spree
class PaymentMethod::CashOnDelivery < PaymentMethod
def actions
%w{purchase capture void}
end
# Indicates whether its possible to capture the payment
def can_capture?(payment)
['checkout', 'pending'].include?(payment.state)
end
# Indicates whether its possible to void the payment.
def can_void?(payment)
payment.state != 'void'
end
def purchase(*args)
throw 'purchase'
end
def capture(*args)
ActiveMerchant::Billing::Response.new(true, "", {}, {})
end
def cancel(response); end
def void(*args)
ActiveMerchant::Billing::Response.new(true, "", {}, {})
end
def source_required?
false
end
def auto_capture?
true
end
end
end
However, that does not raises any exception nor changes payment state. It all looks like i'm doing something wrong, misunderstand something or spree considers my payment methods as non-autocapturable.
Thanks in advance for any clues!
You should first of all need to know about Spree use of State Machine. State of order is changed using this gem. In checkout_controller.rb, there is written "@order.next", this is where stat machine does its part and change states of order accordingly.
This tutorial might help you in understanding how State Machine Gem works.I think most of State Machine code of Spree is present in checkout.rb model.
I think you transaction is happening fine but state does not change because you are not handling State Machine in your class.
You need to understand other flows as well while changing such payment modification. This is one of the most difficult areas of Spree to understand.