Updated to supported latest edge PaymentMethods (very edge)
This commit is contained in:
parent
0bcbdaa0b2
commit
fb0ac7b629
|
@ -0,0 +1,53 @@
|
||||||
|
class PaypalAccount < ActiveRecord::Base
|
||||||
|
has_many :payments, :as => :source
|
||||||
|
|
||||||
|
def finalize!(payment)
|
||||||
|
authorization = find_authorization
|
||||||
|
|
||||||
|
ppx_response = p.payment_method.capture((100 * payment.amount).to_i, authorization.transaction_id)
|
||||||
|
if ppx_response.success?
|
||||||
|
payment = authorization.paypal_payment
|
||||||
|
|
||||||
|
transaction = PaypalTxn.new(:payment => payment,
|
||||||
|
:amount => ppx_response.params["gross_amount"].to_f,
|
||||||
|
:message => ppx_response.params["message"],
|
||||||
|
:payment_status => ppx_response.params["payment_status"],
|
||||||
|
:pending_reason => ppx_response.params["pending_reason"],
|
||||||
|
:transaction_id => ppx_response.params["transaction_id"],
|
||||||
|
:transaction_type => ppx_response.params["transaction_type"],
|
||||||
|
:payment_type => ppx_response.params["payment_type"],
|
||||||
|
:ack => ppx_response.params["ack"],
|
||||||
|
:token => ppx_response.params["token"],
|
||||||
|
:avs_response => ppx_response.avs_result["code"],
|
||||||
|
:cvv_response => ppx_response.cvv_result["code"])
|
||||||
|
|
||||||
|
payment.paypal_txns << transaction
|
||||||
|
|
||||||
|
payment.save
|
||||||
|
else
|
||||||
|
gateway_error(ppx_response)
|
||||||
|
end
|
||||||
|
|
||||||
|
|
||||||
|
end
|
||||||
|
|
||||||
|
|
||||||
|
private
|
||||||
|
def find_authorization(payment)
|
||||||
|
#find the transaction associated with the original authorization/capture
|
||||||
|
txns.find(:first,
|
||||||
|
:conditions => {:pending_reason => "authorization", :payment_status => "Pending"},
|
||||||
|
:order => 'created_at DESC')
|
||||||
|
end
|
||||||
|
|
||||||
|
def find_capture(payment)
|
||||||
|
#find the transaction associated with the original authorization/capture
|
||||||
|
txns.find(:first,
|
||||||
|
:conditions => {:payment_status => "Completed"},
|
||||||
|
:order => 'created_at DESC')
|
||||||
|
end
|
||||||
|
|
||||||
|
def can_capture?(payment)
|
||||||
|
find_capture.nil?
|
||||||
|
end
|
||||||
|
end
|
|
@ -1,23 +0,0 @@
|
||||||
class PaypalPayment < Payment
|
|
||||||
has_many :paypal_txns
|
|
||||||
|
|
||||||
alias :txns :paypal_txns
|
|
||||||
|
|
||||||
def find_authorization
|
|
||||||
#find the transaction associated with the original authorization/capture
|
|
||||||
txns.find(:first,
|
|
||||||
:conditions => {:pending_reason => "authorization", :payment_status => "Pending"},
|
|
||||||
:order => 'created_at DESC')
|
|
||||||
end
|
|
||||||
|
|
||||||
def find_capture
|
|
||||||
#find the transaction associated with the original authorization/capture
|
|
||||||
txns.find(:first,
|
|
||||||
:conditions => {:payment_status => "Completed"},
|
|
||||||
:order => 'created_at DESC')
|
|
||||||
end
|
|
||||||
|
|
||||||
def can_capture?
|
|
||||||
find_capture.nil?
|
|
||||||
end
|
|
||||||
end
|
|
|
@ -1,3 +1,7 @@
|
||||||
class PaypalTxn < ActiveRecord::Base
|
class PaypalTxn < Transaction
|
||||||
belongs_to :paypal_payment
|
enumerable_constant :txn_type, :constants => [:authorize, :capture, :purchase, :void, :credit]
|
||||||
|
|
||||||
|
def txn_type_name
|
||||||
|
TxnType.from_value(txn_type)
|
||||||
|
end
|
||||||
end
|
end
|
||||||
|
|
|
@ -0,0 +1,3 @@
|
||||||
|
<a href="<%= paypal_payment_order_checkout_url @order, :payment_method_id => payment_method %>" style="text-align: center;">
|
||||||
|
<img src="https://www.paypal.com/en_US/i/btn/btn_xpressCheckout.gif" align="left" style="margin-right:7px;"/>
|
||||||
|
</a>
|
|
@ -1,3 +0,0 @@
|
||||||
<a href="<%= paypal_payment_order_checkout_url @checkout.order, :integration_id => integration %>" style="text-align: center;">
|
|
||||||
<img src="https://www.paypal.com/en_US/i/btn/btn_xpressCheckout.gif" align="left" style="margin-right:7px;"/>
|
|
||||||
</a>
|
|
|
@ -0,0 +1,14 @@
|
||||||
|
class CreatePaypalAccounts < ActiveRecord::Migration
|
||||||
|
def self.up
|
||||||
|
create_table :paypal_accounts do |t|
|
||||||
|
t.string :email
|
||||||
|
t.string :payer_id
|
||||||
|
t.string :payer_country
|
||||||
|
t.string :payer_status
|
||||||
|
end
|
||||||
|
end
|
||||||
|
|
||||||
|
def self.down
|
||||||
|
drop_table :paypal_accounts
|
||||||
|
end
|
||||||
|
end
|
|
@ -0,0 +1,26 @@
|
||||||
|
class MakePaypalTxnSti < ActiveRecord::Migration
|
||||||
|
def self.up
|
||||||
|
add_column :transactions, :payment_status, :string
|
||||||
|
add_column :transactions, :message, :string
|
||||||
|
add_column :transactions, :pending_reason, :string
|
||||||
|
add_column :transactions, :transaction_id, :string
|
||||||
|
add_column :transactions, :transaction_type, :string
|
||||||
|
add_column :transactions, :payment_type, :string
|
||||||
|
add_column :transactions, :token, :string
|
||||||
|
|
||||||
|
#to-do migrate existing ppx_txns
|
||||||
|
|
||||||
|
drop_table :paypal_txns
|
||||||
|
|
||||||
|
end
|
||||||
|
|
||||||
|
def self.down
|
||||||
|
remove_column :transactions, :payment_status
|
||||||
|
remove_column :transactions, :message
|
||||||
|
remove_column :transactions, :pending_reason
|
||||||
|
remove_column :transactions, :transaction_id
|
||||||
|
remove_column :transactions, :transaction_type
|
||||||
|
remove_column :transactions, :payment_type
|
||||||
|
remove_column :transactions, :token
|
||||||
|
end
|
||||||
|
end
|
|
@ -5,7 +5,7 @@ module Spree::PaypalExpress
|
||||||
|
|
||||||
def paypal_checkout
|
def paypal_checkout
|
||||||
load_object
|
load_object
|
||||||
opts = all_opts(@order, 'checkout')
|
opts = all_opts(@order, params[:payment_method_id], 'checkout')
|
||||||
opts.merge!(address_options(@order))
|
opts.merge!(address_options(@order))
|
||||||
gateway = paypal_gateway
|
gateway = paypal_gateway
|
||||||
|
|
||||||
|
@ -16,12 +16,12 @@ module Spree::PaypalExpress
|
||||||
return
|
return
|
||||||
end
|
end
|
||||||
|
|
||||||
redirect_to (gateway.redirect_url_for response.token)
|
redirect_to (gateway.redirect_url_for response.token, :review => review)
|
||||||
end
|
end
|
||||||
|
|
||||||
def paypal_payment
|
def paypal_payment
|
||||||
load_object
|
load_object
|
||||||
opts = all_opts(@order, 'payment')
|
opts = all_opts(@order,params[:payment_method_id], 'payment')
|
||||||
opts.merge!(address_options(@order))
|
opts.merge!(address_options(@order))
|
||||||
gateway = paypal_gateway
|
gateway = paypal_gateway
|
||||||
|
|
||||||
|
@ -32,23 +32,28 @@ module Spree::PaypalExpress
|
||||||
return
|
return
|
||||||
end
|
end
|
||||||
|
|
||||||
redirect_to (gateway.redirect_url_for response.token)
|
redirect_to (gateway.redirect_url_for response.token, :review => review)
|
||||||
end
|
end
|
||||||
|
|
||||||
def paypal_confirm
|
def paypal_confirm
|
||||||
load_object
|
load_object
|
||||||
|
|
||||||
opts = { :token => params[:token], :payer_id => params[:PayerID] }.merge all_opts(@order)
|
opts = { :token => params[:token], :payer_id => params[:PayerID] }.merge all_opts(@order, params[:payment_method_id])
|
||||||
gateway = paypal_gateway
|
gateway = paypal_gateway
|
||||||
|
|
||||||
@ppx_details = gateway.details_for params[:token]
|
@ppx_details = gateway.details_for params[:token]
|
||||||
|
|
||||||
if @ppx_details.success?
|
if @ppx_details.success?
|
||||||
# now save the updated order info
|
# now save the updated order info
|
||||||
@order.checkout.email = @ppx_details.email
|
|
||||||
|
PaypalAccount.create(:email => @ppx_details.params["payer"],
|
||||||
|
:payer_id => @ppx_details.params["payer_id"],
|
||||||
|
:payer_country => @ppx_details.params["payer_country"],
|
||||||
|
:payer_status => @ppx_details.params["payer_status"])
|
||||||
|
|
||||||
@order.checkout.special_instructions = @ppx_details.params["note"]
|
@order.checkout.special_instructions = @ppx_details.params["note"]
|
||||||
|
|
||||||
@order.update_attribute(:user, current_user)
|
#@order.update_attribute(:user, current_user)
|
||||||
|
|
||||||
ship_address = @ppx_details.address
|
ship_address = @ppx_details.address
|
||||||
order_ship_address = Address.new :firstname => @ppx_details.params["first_name"],
|
order_ship_address = Address.new :firstname => @ppx_details.params["first_name"],
|
||||||
|
@ -71,7 +76,12 @@ module Spree::PaypalExpress
|
||||||
|
|
||||||
@order.checkout.ship_address = order_ship_address
|
@order.checkout.ship_address = order_ship_address
|
||||||
@order.checkout.save
|
@order.checkout.save
|
||||||
|
|
||||||
|
if review
|
||||||
render :partial => "shared/paypal_express_confirm", :layout => true
|
render :partial => "shared/paypal_express_confirm", :layout => true
|
||||||
|
else
|
||||||
|
paypal_finish
|
||||||
|
end
|
||||||
else
|
else
|
||||||
gateway_error(@ppx_details)
|
gateway_error(@ppx_details)
|
||||||
end
|
end
|
||||||
|
@ -79,9 +89,8 @@ module Spree::PaypalExpress
|
||||||
|
|
||||||
def paypal_finish
|
def paypal_finish
|
||||||
load_object
|
load_object
|
||||||
#order = Order.find_by_number(params[:id])
|
|
||||||
|
|
||||||
opts = { :token => params[:token], :payer_id => params[:PayerID] }.merge all_opts(@order)
|
opts = { :token => params[:token], :payer_id => params[:PayerID] }.merge all_opts(@order, params[:payment_method_id])
|
||||||
gateway = paypal_gateway
|
gateway = paypal_gateway
|
||||||
|
|
||||||
if Spree::Config[:auto_capture]
|
if Spree::Config[:auto_capture]
|
||||||
|
@ -91,23 +100,26 @@ module Spree::PaypalExpress
|
||||||
end
|
end
|
||||||
|
|
||||||
if ppx_auth_response.success?
|
if ppx_auth_response.success?
|
||||||
|
paypal_account = PaypalAccount.find_by_payer_id(params[:PayerID])
|
||||||
|
|
||||||
payment = @order.paypal_payments.create(:amount => ppx_auth_response.params["gross_amount"].to_f)
|
payment = @order.checkout.payments.create(:amount => ppx_auth_response.params["gross_amount"].to_f,
|
||||||
|
:source => paypal_account,
|
||||||
|
:payment_method_id => params[:payment_method_id])
|
||||||
|
|
||||||
transaction = PaypalTxn.new(:paypal_payment => payment,
|
PaypalTxn.create(:payment => payment,
|
||||||
:gross_amount => ppx_auth_response.params["gross_amount"].to_f,
|
:txn_type => PaypalTxn::TxnType::AUTHORIZE,
|
||||||
|
:amount => ppx_auth_response.params["gross_amount"].to_f,
|
||||||
:message => ppx_auth_response.params["message"],
|
:message => ppx_auth_response.params["message"],
|
||||||
:payment_status => ppx_auth_response.params["payment_status"],
|
:payment_status => ppx_auth_response.params["payment_status"],
|
||||||
:pending_reason => ppx_auth_response.params["pending_reason"],
|
:pending_reason => ppx_auth_response.params["pending_reason"],
|
||||||
:transaction_id => ppx_auth_response.params["transaction_id"],
|
:transaction_id => ppx_auth_response.params["transaction_id"],
|
||||||
:transaction_type => ppx_auth_response.params["transaction_type"],
|
:transaction_type => ppx_auth_response.params["transaction_type"],
|
||||||
:payment_type => ppx_auth_response.params["payment_type"],
|
:payment_type => ppx_auth_response.params["payment_type"],
|
||||||
:ack => ppx_auth_response.params["ack"],
|
:response_code => ppx_auth_response.params["ack"],
|
||||||
:token => ppx_auth_response.params["token"],
|
:token => ppx_auth_response.params["token"],
|
||||||
:avs_response => ppx_auth_response.avs_result["code"],
|
:avs_response => ppx_auth_response.avs_result["code"],
|
||||||
:cvv_response => ppx_auth_response.cvv_result["code"])
|
:cvv_response => ppx_auth_response.cvv_result["code"])
|
||||||
|
|
||||||
payment.paypal_txns << transaction
|
|
||||||
|
|
||||||
@order.save!
|
@order.save!
|
||||||
@checkout.reload
|
@checkout.reload
|
||||||
|
@ -135,15 +147,16 @@ module Spree::PaypalExpress
|
||||||
if ppx_response.success?
|
if ppx_response.success?
|
||||||
payment = authorization.paypal_payment
|
payment = authorization.paypal_payment
|
||||||
|
|
||||||
transaction = PaypalTxn.new(:paypal_payment => payment,
|
transaction = PaypalTxn.new(:payment => payment,
|
||||||
:gross_amount => ppx_response.params["gross_amount"].to_f,
|
:txn_type => PaypalTxn::TxnType::CAPTURE,
|
||||||
|
:amount => ppx_response.params["gross_amount"].to_f,
|
||||||
:message => ppx_response.params["message"],
|
:message => ppx_response.params["message"],
|
||||||
:payment_status => ppx_response.params["payment_status"],
|
:payment_status => ppx_response.params["payment_status"],
|
||||||
:pending_reason => ppx_response.params["pending_reason"],
|
:pending_reason => ppx_response.params["pending_reason"],
|
||||||
:transaction_id => ppx_response.params["transaction_id"],
|
:transaction_id => ppx_response.params["transaction_id"],
|
||||||
:transaction_type => ppx_response.params["transaction_type"],
|
:transaction_type => ppx_response.params["transaction_type"],
|
||||||
:payment_type => ppx_response.params["payment_type"],
|
:payment_type => ppx_response.params["payment_type"],
|
||||||
:ack => ppx_response.params["ack"],
|
:response_code => ppx_response.params["ack"],
|
||||||
:token => ppx_response.params["token"],
|
:token => ppx_response.params["token"],
|
||||||
:avs_response => ppx_response.avs_result["code"],
|
:avs_response => ppx_response.avs_result["code"],
|
||||||
:cvv_response => ppx_response.cvv_result["code"])
|
:cvv_response => ppx_response.cvv_result["code"])
|
||||||
|
@ -185,6 +198,12 @@ module Spree::PaypalExpress
|
||||||
|
|
||||||
private
|
private
|
||||||
def fixed_opts
|
def fixed_opts
|
||||||
|
if Spree::Config[:paypal_express_local_confirm].nil?
|
||||||
|
user_action = "continue"
|
||||||
|
else
|
||||||
|
user_action = Spree::Config[:paypal_express_local_confirm] == "t" ? "continue" : "commit"
|
||||||
|
end
|
||||||
|
|
||||||
{ :description => "Goods from #{Spree::Config[:site_name]}", # site details...
|
{ :description => "Goods from #{Spree::Config[:site_name]}", # site details...
|
||||||
|
|
||||||
#:page_style => "foobar", # merchant account can set named config
|
#:page_style => "foobar", # merchant account can set named config
|
||||||
|
@ -198,6 +217,7 @@ module Spree::PaypalExpress
|
||||||
:notify_url => 'to be done', # this is a callback, not tried it yet
|
:notify_url => 'to be done', # this is a callback, not tried it yet
|
||||||
|
|
||||||
:req_confirm_shipping => false, # for security, might make an option later
|
:req_confirm_shipping => false, # for security, might make an option later
|
||||||
|
:user_action => user_action
|
||||||
|
|
||||||
# WARNING -- don't use :ship_discount, :insurance_offered, :insurance since
|
# WARNING -- don't use :ship_discount, :insurance_offered, :insurance since
|
||||||
# they've not been tested and may trigger some paypal bugs, eg not showing order
|
# they've not been tested and may trigger some paypal bugs, eg not showing order
|
||||||
|
@ -205,7 +225,7 @@ module Spree::PaypalExpress
|
||||||
}
|
}
|
||||||
end
|
end
|
||||||
|
|
||||||
def order_opts(order, stage)
|
def order_opts(order, payment_method, stage)
|
||||||
items = order.line_items.map do |item|
|
items = order.line_items.map do |item|
|
||||||
tax = paypal_variant_tax(item.price, item.variant)
|
tax = paypal_variant_tax(item.price, item.variant)
|
||||||
price = (item.price * 100).to_i # convert for gateway
|
price = (item.price * 100).to_i # convert for gateway
|
||||||
|
@ -223,7 +243,7 @@ module Spree::PaypalExpress
|
||||||
end
|
end
|
||||||
|
|
||||||
|
|
||||||
opts = { :return_url => request.protocol + request.host_with_port + "/orders/#{order.number}/checkout/paypal_confirm",
|
opts = { :return_url => request.protocol + request.host_with_port + "/orders/#{order.number}/checkout/paypal_confirm?payment_method_id=#{payment_method}",
|
||||||
:cancel_return_url => "http://" + request.host_with_port + "/orders/#{order.number}/edit",
|
:cancel_return_url => "http://" + request.host_with_port + "/orders/#{order.number}/edit",
|
||||||
:order_id => order.number,
|
:order_id => order.number,
|
||||||
:custom => order.number,
|
:custom => order.number,
|
||||||
|
@ -285,9 +305,8 @@ module Spree::PaypalExpress
|
||||||
}
|
}
|
||||||
end
|
end
|
||||||
|
|
||||||
def all_opts(order, stage=nil)
|
def all_opts(order, payment_method, stage=nil)
|
||||||
opts = fixed_opts.merge(order_opts(order, stage))#.
|
opts = fixed_opts.merge(order_opts(order, payment_method, stage))
|
||||||
# merge(paypal_site_options order) BQ
|
|
||||||
|
|
||||||
if stage == "payment"
|
if stage == "payment"
|
||||||
opts.merge! flat_rate_shipping_and_handling_options(order, stage)
|
opts.merge! flat_rate_shipping_and_handling_options(order, stage)
|
||||||
|
@ -334,9 +353,16 @@ module Spree::PaypalExpress
|
||||||
|
|
||||||
# create the gateway from the supplied options
|
# create the gateway from the supplied options
|
||||||
def paypal_gateway
|
def paypal_gateway
|
||||||
integration = BillingIntegration.find(params[:integration_id]) if params.key? :integration_id
|
integration = PaymentMethod.find(params[:payment_method_id])
|
||||||
integration ||= BillingIntegration.current
|
|
||||||
|
|
||||||
gateway = integration.provider
|
gateway = integration.provider
|
||||||
end
|
end
|
||||||
|
|
||||||
|
# if you want to confirm the order on Paypal's site, then this needs to return false
|
||||||
|
def review
|
||||||
|
if Spree::Config[:paypal_express_review].nil?
|
||||||
|
true
|
||||||
|
else
|
||||||
|
Spree::Config[:paypal_express_review] == "t" ? true : false
|
||||||
|
end
|
||||||
|
end
|
||||||
end
|
end
|
||||||
|
|
Loading…
Reference in New Issue