Skip to content

Commit

Permalink
Worldpay: Encyrpted ApplePay and GooglePay
Browse files Browse the repository at this point in the history
Add support for encrypted ApplePay and GooglePay.
  • Loading branch information
Alma Malambo committed May 15, 2024
1 parent 9a51b19 commit 0c95361
Show file tree
Hide file tree
Showing 3 changed files with 76 additions and 3 deletions.
2 changes: 1 addition & 1 deletion CHANGELOG
Original file line number Diff line number Diff line change
Expand Up @@ -163,7 +163,7 @@
* Cybersource Rest: Add support for network tokens [aenand] #5107
* Decidir: Add support for customer object [rachelkirk] #5071
* Worldpay: Add support for stored credentials with network tokens [aenand] #5114

* Worldpay: Encyrpted ApplePay and GooglePay [almalee24] #5093

== Version 1.135.0 (August 24, 2023)
* PaymentExpress: Correct endpoints [steveh] #4827
Expand Down
25 changes: 24 additions & 1 deletion lib/active_merchant/billing/gateways/worldpay.rb
Original file line number Diff line number Diff line change
Expand Up @@ -577,6 +577,8 @@ def add_payment_method(xml, amount, payment_method, options)
add_amount_for_pay_as_order(xml, amount, payment_method, options)
when :network_token
add_network_tokenization_card(xml, payment_method, options)
when :encrypted_wallet
add_encrypted_wallet(xml, payment_method, options)
else
add_card_or_token(xml, payment_method, options)
end
Expand Down Expand Up @@ -617,6 +619,23 @@ def add_network_tokenization_card(xml, payment_method, options)
end
end

def add_encrypted_wallet(xml, payment_method, options)
source = payment_method.source == :apple_pay ? 'APPLEPAY' : 'PAYWITHGOOGLE'

xml.paymentDetails do
xml.tag! "#{source}-SSL" do
xml.header do
xml.ephemeralPublicKey payment_method.payment_data.dig(:header, :ephemeralPublicKey)
xml.publicKeyHash payment_method.payment_data.dig(:header, :publicKeyHash)
xml.transactionId payment_method.payment_data.dig(:header, :transactionId)
end
xml.signature payment_method.payment_data[:signature]
xml.version payment_method.payment_data[:version]
xml.data payment_method.payment_data[:data]
end
end
end

def add_card_or_token(xml, payment_method, options)
xml.paymentDetails credit_fund_transfer_attribute(options) do
if options[:payment_type] == :token
Expand Down Expand Up @@ -986,7 +1005,11 @@ def payment_details(payment_method, options = {})
when String
token_type_and_details(payment_method)
else
type = network_token?(payment_method) || options[:wallet_type] == :google_pay ? :network_token : :credit
type = if network_token?(payment_method)
payment_method.payment_data ? :encrypted_wallet : :network_token
else
options[:wallet_type] == :google_pay ? :network_token : :credit
end

{ payment_type: type }
end
Expand Down
52 changes: 51 additions & 1 deletion test/unit/gateways/worldpay_test.rb
Original file line number Diff line number Diff line change
Expand Up @@ -164,7 +164,7 @@ def test_payment_type_for_network_card

def test_payment_type_returns_network_token_if_the_payment_method_responds_to_source_payment_cryptogram_and_eci
payment_method = mock
payment_method.stubs(source: nil, payment_cryptogram: nil, eci: nil)
payment_method.stubs(source: nil, payment_cryptogram: nil, eci: nil, payment_data: nil)
result = @gateway.send(:payment_details, payment_method)
assert_equal({ payment_type: :network_token }, result)
end
Expand Down Expand Up @@ -219,6 +219,56 @@ def test_successful_authorize_without_name
assert_equal 'R50704213207145707', response.authorization
end

def test_successful_authorize_encrypted_apple_pay
apple_pay = ActiveMerchant::Billing::NetworkTokenizationCreditCard.new({
source: :apple_pay,
payment_data: {
version: 'EC_v1',
data: 'QlzLxRFnNP9/GTaMhBwgmZ2ywntbr9',
signature: 'signature',
header: {
ephemeralPublicKey: 'ephemeralPublicKey',
publicKeyHash: 'publicKeyHash',
transactionId: 'transactionId'
}
}
})

stub_comms do
@gateway.authorize(@amount, apple_pay, @options)
end.check_request do |_endpoint, data, _headers|
assert_match(/APPLEPAY-SSL/, data)
assert_match(%r(<version>EC_v1</version>), data)
assert_match(%r(<transactionId>transactionId</transactionId>), data)
assert_match(%r(<data>QlzLxRFnNP9/GTaMhBwgmZ2ywntbr9</data>), data)
end.respond_with(successful_authorize_response)
end

def test_successful_authorize_encrypted_google_pay
google_pay = ActiveMerchant::Billing::NetworkTokenizationCreditCard.new({
source: :google_pay,
payment_data: {
version: 'EC_v1',
data: 'QlzLxRFnNP9/GTaMhBwgmZ2ywntbr9',
signature: 'signature',
header: {
ephemeralPublicKey: 'ephemeralPublicKey',
publicKeyHash: 'publicKeyHash',
transactionId: 'transactionId'
}
}
})

stub_comms do
@gateway.authorize(@amount, google_pay, @options)
end.check_request do |_endpoint, data, _headers|
assert_match(/PAYWITHGOOGLE-SSL/, data)
assert_match(%r(<version>EC_v1</version>), data)
assert_match(%r(<transactionId>transactionId</transactionId>), data)
assert_match(%r(<data>QlzLxRFnNP9/GTaMhBwgmZ2ywntbr9</data>), data)
end.respond_with(successful_authorize_response)
end

def test_successful_authorize_by_reference
response = stub_comms do
@gateway.authorize(@amount, @options[:order_id].to_s, @options)
Expand Down

0 comments on commit 0c95361

Please sign in to comment.