activemerchant 1.123.0 → 1.125.0

Sign up to get free protection for your applications and to get access to all the features.
Files changed (48) hide show
  1. checksums.yaml +4 -4
  2. data/CHANGELOG +131 -0
  3. data/lib/active_merchant/billing/check.rb +5 -8
  4. data/lib/active_merchant/billing/credit_card.rb +10 -0
  5. data/lib/active_merchant/billing/credit_card_methods.rb +6 -3
  6. data/lib/active_merchant/billing/gateway.rb +1 -1
  7. data/lib/active_merchant/billing/gateways/adyen.rb +61 -9
  8. data/lib/active_merchant/billing/gateways/card_stream.rb +17 -13
  9. data/lib/active_merchant/billing/gateways/cashnet.rb +15 -5
  10. data/lib/active_merchant/billing/gateways/checkout_v2.rb +33 -4
  11. data/lib/active_merchant/billing/gateways/cyber_source.rb +11 -3
  12. data/lib/active_merchant/billing/gateways/d_local.rb +12 -6
  13. data/lib/active_merchant/billing/gateways/decidir_plus.rb +173 -0
  14. data/lib/active_merchant/billing/gateways/ebanx.rb +16 -1
  15. data/lib/active_merchant/billing/gateways/elavon.rb +6 -3
  16. data/lib/active_merchant/billing/gateways/element.rb +20 -2
  17. data/lib/active_merchant/billing/gateways/global_collect.rb +111 -16
  18. data/lib/active_merchant/billing/gateways/ipg.rb +416 -0
  19. data/lib/active_merchant/billing/gateways/kushki.rb +7 -0
  20. data/lib/active_merchant/billing/gateways/mercado_pago.rb +3 -1
  21. data/lib/active_merchant/billing/gateways/mit.rb +260 -0
  22. data/lib/active_merchant/billing/gateways/moka.rb +24 -11
  23. data/lib/active_merchant/billing/gateways/mundipagg.rb +8 -6
  24. data/lib/active_merchant/billing/gateways/nmi.rb +15 -1
  25. data/lib/active_merchant/billing/gateways/orbital.rb +19 -3
  26. data/lib/active_merchant/billing/gateways/pay_arc.rb +9 -7
  27. data/lib/active_merchant/billing/gateways/pay_conex.rb +3 -1
  28. data/lib/active_merchant/billing/gateways/pay_trace.rb +1 -1
  29. data/lib/active_merchant/billing/gateways/payflow.rb +14 -6
  30. data/lib/active_merchant/billing/gateways/paymentez.rb +9 -2
  31. data/lib/active_merchant/billing/gateways/paysafe.rb +144 -23
  32. data/lib/active_merchant/billing/gateways/payu_latam.rb +6 -1
  33. data/lib/active_merchant/billing/gateways/payway_dot_com.rb +3 -3
  34. data/lib/active_merchant/billing/gateways/pin.rb +31 -4
  35. data/lib/active_merchant/billing/gateways/priority.rb +347 -0
  36. data/lib/active_merchant/billing/gateways/realex.rb +18 -0
  37. data/lib/active_merchant/billing/gateways/safe_charge.rb +6 -2
  38. data/lib/active_merchant/billing/gateways/stripe.rb +27 -7
  39. data/lib/active_merchant/billing/gateways/stripe_payment_intents.rb +96 -38
  40. data/lib/active_merchant/billing/gateways/trans_first_transaction_express.rb +2 -1
  41. data/lib/active_merchant/billing/gateways/trust_commerce.rb +2 -1
  42. data/lib/active_merchant/billing/gateways/usa_epay_transaction.rb +20 -6
  43. data/lib/active_merchant/billing/gateways/wompi.rb +193 -0
  44. data/lib/active_merchant/billing/gateways/worldpay.rb +196 -64
  45. data/lib/active_merchant/billing/network_tokenization_credit_card.rb +1 -1
  46. data/lib/active_merchant/billing/response.rb +4 -0
  47. data/lib/active_merchant/version.rb +1 -1
  48. metadata +7 -2
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: ce71317ac7aa50f5b0bcbfb6fe301f804eea7919153b9ade64cbd0d34ea7a25c
4
- data.tar.gz: a62776247abfdb56c2a0cb36e336242191b3809d989999aebb7a906f8b7afa9b
3
+ metadata.gz: 9f8d0ad7bb54e228b44738e6cf324034467970e6709047a7f799dd7d3276998c
4
+ data.tar.gz: 96ab0828793d536f7df925fe962444c1cc0c48d129de54c19d40c81145ed1d11
5
5
  SHA512:
6
- metadata.gz: 83869085801337d35208b4c41cfebe89e315a9ea9590acb8b168402ab3acf398df011a201dcafd85139af7d01c3b75b35e278b18cd5bc7198655606181fd17ea
7
- data.tar.gz: 60a54eae2330f8d00959931d933025cd32f302144c37e17a5d11d35ebd3f3356bb80fc8cfb15f3b060410782a667bdae985f07442bd9af4d9a9f03e5df2faa88
6
+ metadata.gz: 1a31f43e0702edeb5727c61285c54afeecc5accc6c9f89134966228fe9c08369f9918890ff25cda85ec863f3cda2bd1e2e6dde8f4eed1254ed6d520f37067dcd
7
+ data.tar.gz: 144dc89e223d28ceed1399b50d15116d169dc056f878bb9ba9ed477e4c141fde2c2bc25a882610e4295fa3a25fc8f63800034352b77eb3a370718ea64d017665
data/CHANGELOG CHANGED
@@ -1,7 +1,138 @@
1
+
1
2
  = ActiveMerchant CHANGELOG
2
3
 
3
4
  == HEAD
4
5
 
6
+ == Version 1.125.0 (January 20, 2022)
7
+ * Wompi: support gateway [therufs] #4173
8
+ * Stripe Payment Intents: Add setup_purchase [aenand] #4178
9
+ * Ipg: Add new gateway [ajawadmirza] #4171
10
+ * Worldpay: Adding support for google pay and apple pay [cristian] #4180
11
+ * Worldpay: Adding scrubbing for network token transactions [cristian] #4181
12
+ * SafeCharge: Add sg_NotUseCVV field [ajawadmirza] #4177
13
+ * PayULatam: Correctly map maestro and condensa card types [dsmcclain] #4182
14
+ * StripePaymentIntents: Refactor response for setup_purchase [aenand] #4183
15
+ * Wompi: cast error messages to JSON [therufs] #4186
16
+ * NMI: Omit initial_transaction_id for CIT [aenand] #4189
17
+ * Priority: Support Priority Payment Systems gateway [jessiagee] #4166
18
+ * GlobalCollect: Support for Lodging Data [naashton] #4190
19
+ * IPG: Add support for sub-merchant and recurring type fields [ajawadmirza] # 4188
20
+ * Wompi: Support `installments` option [therufs] #4192
21
+ * Stripe PI: add support for `fulfillment_date` and `event_type` [dsmcclain] #4193
22
+ * Paysafe: Adjust logic for sending 3DS field [meagabeth] #4194
23
+ * Priority: Fix unit test cases [ajawadmirza] #4195
24
+ * EBANX: New Gateway Specific Receiver [spreedly-kledoux] #4198
25
+ * Wompi: Don't send CVV field if no CVV provided [therufs] #4199
26
+ * Worldpay: cleaning order_id according to worldpay rules [cristian] #4197
27
+ * Paysafe: Concatenate credentials for headers [meagabeth] #4201
28
+ * Stripe Payment Intents: Add metadata to setup_purchase [aenand] #4202
29
+ * Priority: Add gateway standard changes [ajawadmirza] #4200
30
+ * IPG: Add support for payment by token [ajawadmirza] #4191
31
+ * Element (Vantiv Express): Add support for general credit [dsmcclain] #4203
32
+ * Worldpay: Update supported countries list, currencies [jherreraa] #4207
33
+ * StripePI: Adding countries available. [gasb150] #4208
34
+ * Orbital: Adding google pay payment tests for Orbital. [ajawadmirza] #4205
35
+ * Bug: Fixing supported countries method when there is inheritance involved [cristian] #4211
36
+ * Mundipagg: Update success method [ajawadmirza] #4210
37
+ * Worldpay: Add support for Visa Direct Fast Funds Credit [dsmcclain] #4212
38
+ * Paysafe: Add support for stored credentials [meagabeth] #4214
39
+ * Worldpay: Adding missing countries to supported countries [cristian] #4213
40
+ * Update institution numbers for Canadian banks [therufs] #4216
41
+ * Worldpay: Set default eCommerce indicator for EMVCO network tokens [shasum] #4215
42
+ * Update handling routing numbers for Canadian banks [therufs] #4217
43
+ * Stripe: API version updated [jherreraa] #4209
44
+ * Mercado Pago: Update verify method [ajawadmirza] #4219
45
+ * DLocal: Set API Version [gasb150] #4222
46
+ * Wompi: Add support for Authorize and Capture [rachelkirk] #4218
47
+ * Priority: Update source and billing address checks [jessiagee] #4220
48
+ * Pin Payments: Add support for `diners_club`, `discover`, and `jcb` cardtypes [montdidier] #4142
49
+ * USA ePay: Add store method [ajawadmirza] #4224
50
+ * IPG: Quick fix to remove warning [ajawadmirza] #4225
51
+ * Remove YAML warning on load_fixtures_method [jherreraa] #4226
52
+ * Worldpay: Add support for tokenizing payment methods with transaction identifiers [dsmcclain] #4227
53
+ * USA ePay: Update implementation to send valid authorization [ajawadmirza] #4231
54
+ * USA ePay: Add store test, update authorize param [jessiagee] #4232
55
+ * Stripe: Update destination test account [jherreraa] #4234
56
+ * Add skip_response option on request check for commit stubs [cristian] #4223
57
+ * Pin Payments: Add support for `void` and New Zealand to supported countries. [montdidier] #4144
58
+ * Wompi: Update authorization in `capture` method. [rachelkirk] #4238
59
+ * IPG: Update authorization to support `store` method token. [ajawadmirza] #4233
60
+ * Paymentez: Update card mappings [ajawadmirza] #4237
61
+ * Priority: Update parsing for error messages [jessiagee] #4245
62
+ * GlobalCollect: Support for Airline Data [naashton] #4187
63
+ * IPG: Add `tpv_error_code` and `tpv_error_msg` fields [ajawadmirza] #4241
64
+ * StripePI: Set restriction for Apple/Google Pay [jherreraa] #4247
65
+ * Cashnet: support multiple itemcodes and amounts [peteroas] #4243
66
+ * IPG: Send default currency in `verify` and two digit `ExpMonth` [ajawadmirza] #4244
67
+ * Stripe: Add remote tests set up to avoid exceed the max external accounts limit [jherreraa] #4239
68
+ * Stripe: Add support for `radar_options: skip_rules` [dsmcclain] #4250
69
+ * CyberSource: Add `user_po`, `taxable`, `national_tax_indicator`, `tax_amount`, and `national_tax` fields [ajawadmirza] #4251
70
+ * Kushki: Add support for `metadata` [rachelkirk] #4253
71
+ * IPG: Add `redact` operation [ajawadmirza] #4254
72
+ * Wompi: Update sandbox and production endpoints [rachelkirk] #4255
73
+ * Orbital: Add `sca_merchant_initiated` operation [ajawadmirza] #4256
74
+ * Cashnet: convert amounts to integers for proper gateway handling [peteroas] #2207
75
+ * PayTrace: Add `unstore` operation [ajawadmirza] #4262
76
+ * Decidir Plus: Add gateway adapter [naashton] #4264
77
+ * CheckoutV2: Add support for Apple Pay and Google Pay tokens [AMHOL] #4235
78
+ * Decidir Plus: Update payment reference [naashton] #4271
79
+ * Paysafe: Update redact method [meagabeth] #4269
80
+ * CyberSource: Add `line_items` field in authorize method [ajawadmirza] #4268
81
+ * CheckoutV2: Support processing channel and marketplace sub entity ID [AMHOL] #4236
82
+ * Elavon: `third_party_token` bug fix [rachelkirk] #4273
83
+ * Decidir Plus: Add `sub_payments` field [naashton] #4274
84
+ * Pin Payments: Add `unstore` support [montdidier] #4276
85
+ * Orbital: Add support for $0 verify [javierpedrozaing] #4275
86
+ * Update inline documentation with all supported cardtypes [ali-hassan] #4283
87
+ * PayWay: Update endpoints, response code [jessiagee] #4281
88
+ * CyberSource: Add `line_items` for purchase [ajawadmirza] #4282
89
+
90
+ == Version 1.124.0 (October 28th, 2021)
91
+ * Worldpay: Add Support for Submerchant Data on Worldpay [almalee24] #4147
92
+ * dlocal: Add device_id and ip to payer object and add additional_data [aenand] #4116
93
+ * Adyen: Add network tokenization support to Adyen gateway [mymir] #4101
94
+ * Adyen: Add ACH Support [almalee24] #4105
95
+ * Moka: Support 3DS endpoint and update test url [dsmcclain] #4110
96
+ * Paysafe: Adjust profile data [meagabeth] #4112
97
+ * Stripe Payment Intents: Add support for claim_without_transaction_id field [BritneyS] #4111
98
+ * Mit: Add New Gateway [EsporaInfra] #3820
99
+ * Routex: add card type [rachelkirk] #4115
100
+ * Orbital: Scrub Payment Cryptogram [naashton] #4121
101
+ * Paysafe: Add support for airline fields [meagabeth] #4120
102
+ * Stripe and Stripe PI: Add Radar Session Option [tatsianaclifton] #4119
103
+ * PayArc: Fix billing address nil and phone_number issues [dsmcclain] #4114
104
+ * Routex: Update BIN numbers [rachelkirk] #4123
105
+ * UnionPay: Add Stripe's UnionPay test card to UnionPay BIN range #4122
106
+ * GlobalCollect: Support URL override [naashton] #4127
107
+ * PayConex: scrub bank account info from transcripts [mbreenlyles] #4128
108
+ * Moka: Remove additional transaction data from subsequent calls [naashton] #4129
109
+ * Moka: Ensure CvcNumber can be an empty string [jessiagee] #4130
110
+ * Maestro: Allow more card lengths for Luhnless bins [therufs] #4131
111
+ * Paysafe: Update supported countries [meagabeth] #4135
112
+ * Paysafe: Update field mapping for split_pay [meagabeth] #4136
113
+ * SafeCharge: Add handling for non-fractional currencies [dsmcclain] #4137
114
+ * CardStream: Support passing country_code in request [dsmcclain] #4139
115
+ * Adyen: Adjust phone number mapping [aenand] #4138
116
+ * Mit: Change how parameters are converted to JSON [tatsianaclifton] #4140
117
+ * Stripe: Add account_number to scrubbing [aenand] #4145
118
+ * Stripe PI: add name on card to billing_details [dsmcclain] #4146
119
+ * TrustCommerce: Scrub bank account info [mbreenlyles] #4149
120
+ * TransFirst: Scrub account number [aenand] #4152
121
+ * Paysafe: Update supported countries list [meagabeth] #4154
122
+ * dLocal: Update supported countries list [mbreenlyles] #4155
123
+ * SafeCharge: Add support for email field in capture [rachelkirk] #4153
124
+ * Paysafe: Remove invalid code [meagabeth] #4156
125
+ * NMI: Add descriptor fields [ajawadmirza] #4157
126
+ * Authorize.net: Add tests for scrubbing banking account info (in addition to BluePay, BridgePay, Forte, HPS, and Vanco Gateways)[aenand] #4159
127
+ * Moka: Send refund amount with decimal [dsmcclain] #4160
128
+ * GlobalCollect: Append URI to the URL [naashton] #4162
129
+ * Adyen: Add application info fields [aenand] #4163
130
+ * Adyen: Send NTID from stored cred hash [curiousepic] #4164
131
+ * Payflow: use proper case for 3DS 2.x element names [bbraschi] #4113
132
+ * Realex: Add support for stored credentials [dsmcclain] #4170
133
+ * Moka: Add support for InstallmentNumber field [dsmcclain] #4172
134
+ * Payflow: include AuthenticationStatus for 3DS 2.x [bbraschi] #4168
135
+
5
136
  == Version 1.123.0 (September 10th, 2021)
6
137
  * Paysafe: Add gateway integration [meagabeth] #4085
7
138
  * Elavon: Support recurring transactions with stored credentials [cdmackeyfree] #4086
@@ -14,13 +14,13 @@ module ActiveMerchant #:nodoc:
14
14
  attr_accessor :institution_number, :transit_number
15
15
 
16
16
  # Canadian Institution Numbers
17
- # Found here: https://en.wikipedia.org/wiki/Routing_number_(Canada)
17
+ # Partial list found here: https://en.wikipedia.org/wiki/Routing_number_(Canada)
18
18
  CAN_INSTITUTION_NUMBERS = %w(
19
- 001 002 003 004 006 010 016 030 039 117 127 177 219 245 260 269 270 308
20
- 309 310 315 320 338 340 509 540 608 614 623 809 815 819 828 829 837 839
19
+ 001 002 003 004 006 010 016 030 039 117 127 177 219 245 260 269 270 308
20
+ 309 310 315 320 338 340 509 540 608 614 623 809 815 819 828 829 837 839
21
21
  865 879 889 899 241 242 248 250 265 275 277 290 294 301 303 307 311 314
22
22
  321 323 327 328 330 332 334 335 342 343 346 352 355 361 362 366 370 372
23
- 376 378 807 853
23
+ 376 378 807 853 890
24
24
  )
25
25
 
26
26
  def name
@@ -71,11 +71,8 @@ module ActiveMerchant #:nodoc:
71
71
  (7 * (digits[1] + digits[4] + digits[7])) +
72
72
  (digits[2] + digits[5] + digits[8])) % 10
73
73
 
74
- return checksum == 0
74
+ return checksum == 0 || CAN_INSTITUTION_NUMBERS.include?(routing_number[1..3])
75
75
  end
76
-
77
- return CAN_INSTITUTION_NUMBERS.include?(routing_number[0..2]) if digits.size == 8
78
-
79
76
  false
80
77
  end
81
78
  end
@@ -18,6 +18,11 @@ module ActiveMerchant #:nodoc:
18
18
  # * Dankort
19
19
  # * Maestro
20
20
  # * Forbrugsforeningen
21
+ # * Sodexo
22
+ # * Vr
23
+ # * Carnet
24
+ # * Synchrony
25
+ # * Routex
21
26
  # * Elo
22
27
  # * Alelo
23
28
  # * Cabal
@@ -97,6 +102,11 @@ module ActiveMerchant #:nodoc:
97
102
  # * +'dankort'+
98
103
  # * +'maestro'+
99
104
  # * +'forbrugsforeningen'+
105
+ # * +'sodexo'+
106
+ # * +'vr'+
107
+ # * +'carnet'+
108
+ # * +'synchrony'+
109
+ # * +'routex'+
100
110
  # * +'elo'+
101
111
  # * +'alelo'+
102
112
  # * +'cabal'+
@@ -1,3 +1,5 @@
1
+ require 'set'
2
+
1
3
  module ActiveMerchant #:nodoc:
2
4
  module Billing #:nodoc:
3
5
  # Convenience methods that can be included into a custom Credit Card object, such as an ActiveRecord based Credit Card object.
@@ -19,7 +21,7 @@ module ActiveMerchant #:nodoc:
19
21
  MAESTRO_BINS.any? { |bin| num.slice(0, bin.size) == bin }
20
22
  )
21
23
  },
22
- 'maestro_no_luhn' => ->(num) { num =~ /^(501080|501081|501082)\d{10}$/ },
24
+ 'maestro_no_luhn' => ->(num) { num =~ /^(501080|501081|501082)\d{6,13}$/ },
23
25
  'forbrugsforeningen' => ->(num) { num =~ /^600722\d{10}$/ },
24
26
  'sodexo' => ->(num) { num =~ /^(606071|603389|606070|606069|606068|600818)\d{10}$/ },
25
27
  'alia' => ->(num) { num =~ /^(504997|505878|601030|601073|505874)\d{10}$/ },
@@ -35,7 +37,8 @@ module ActiveMerchant #:nodoc:
35
37
  'olimpica' => ->(num) { num =~ /^636853\d{10}$/ },
36
38
  'creditel' => ->(num) { num =~ /^601933\d{10}$/ },
37
39
  'confiable' => ->(num) { num =~ /^560718\d{10}$/ },
38
- 'synchrony' => ->(num) { num =~ /^700600\d{10}$/ }
40
+ 'synchrony' => ->(num) { num =~ /^700600\d{10}$/ },
41
+ 'routex' => ->(num) { num =~ /^(700676|700678)\d{13}$/ }
39
42
  }
40
43
 
41
44
  # http://www.barclaycard.co.uk/business/files/bin_rules.pdf
@@ -198,7 +201,7 @@ module ActiveMerchant #:nodoc:
198
201
 
199
202
  # https://www.discoverglobalnetwork.com/content/dam/discover/en_us/dgn/pdfs/IPP-VAR-Enabler-Compliance.pdf
200
203
  UNIONPAY_RANGES = [
201
- 62212600..62379699, 62400000..62699999, 62820000..62889999,
204
+ 62000000..62000000, 62212600..62379699, 62400000..62699999, 62820000..62889999,
202
205
  81000000..81099999, 81100000..81319999, 81320000..81519999, 81520000..81639999, 81640000..81719999
203
206
  ]
204
207
 
@@ -162,7 +162,7 @@ module ActiveMerchant #:nodoc:
162
162
  end
163
163
 
164
164
  def self.supported_countries
165
- @supported_countries ||= []
165
+ @supported_countries ||= (self.superclass.supported_countries || [])
166
166
  end
167
167
 
168
168
  def supported_countries
@@ -60,6 +60,7 @@ module ActiveMerchant #:nodoc:
60
60
  add_splits(post, options)
61
61
  add_recurring_contract(post, options)
62
62
  add_network_transaction_reference(post, options)
63
+ add_application_info(post, options)
63
64
  commit('authorise', post, options)
64
65
  end
65
66
 
@@ -82,12 +83,13 @@ module ActiveMerchant #:nodoc:
82
83
  end
83
84
 
84
85
  def credit(money, payment, options = {})
86
+ action = 'refundWithData'
85
87
  post = init_post(options)
86
88
  add_invoice(post, money, options)
87
- add_payment(post, payment, options)
89
+ add_payment(post, payment, options, action)
88
90
  add_shopper_reference(post, options)
89
91
  add_network_transaction_reference(post, options)
90
- commit('refundWithData', post, options)
92
+ commit(action, post, options)
91
93
  end
92
94
 
93
95
  def void(authorization, options = {})
@@ -152,12 +154,19 @@ module ActiveMerchant #:nodoc:
152
154
  true
153
155
  end
154
156
 
157
+ def supports_network_tokenization?
158
+ true
159
+ end
160
+
155
161
  def scrub(transcript)
156
162
  transcript.
157
163
  gsub(%r((Authorization: Basic )\w+), '\1[FILTERED]').
158
- gsub(%r(("number\\?":\\?")[^"]*)i, '\1[FILTERED]').
159
- gsub(%r(("cvc\\?":\\?")[^"]*)i, '\1[FILTERED]').
160
- gsub(%r(("cavv\\?":\\?")[^"]*)i, '\1[FILTERED]')
164
+ gsub(%r(("number\\?"\s*:\s*\\?")[^"]*)i, '\1[FILTERED]').
165
+ gsub(%r(("cvc\\?"\s*:\s*\\?")[^"]*)i, '\1[FILTERED]').
166
+ gsub(%r(("cavv\\?"\s*:\s*\\?")[^"]*)i, '\1[FILTERED]').
167
+ gsub(%r(("bankLocationId\\?"\s*:\s*\\?")[^"]*)i, '\1[FILTERED]').
168
+ gsub(%r(("iban\\?"\s*:\s*\\?")[^"]*)i, '\1[FILTERED]').
169
+ gsub(%r(("bankAccountNumber\\?"\s*:\s*\\?")[^"]*)i, '\1[FILTERED]')
161
170
  end
162
171
 
163
172
  private
@@ -209,7 +218,7 @@ module ActiveMerchant #:nodoc:
209
218
  }
210
219
 
211
220
  def add_extra_data(post, payment, options)
212
- post[:telephoneNumber] = options[:billing_address][:phone] if options.dig(:billing_address, :phone)
221
+ post[:telephoneNumber] = (options[:billing_address][:phone_number] if options.dig(:billing_address, :phone_number)) || (options[:billing_address][:phone] if options.dig(:billing_address, :phone)) || ''
213
222
  post[:fraudOffset] = options[:fraud_offset] if options[:fraud_offset]
214
223
  post[:selectedBrand] = options[:selected_brand] if options[:selected_brand]
215
224
  post[:selectedBrand] ||= NETWORK_TOKENIZATION_CARD_SOURCE[payment.source.to_s] if payment.is_a?(NetworkTokenizationCreditCard)
@@ -332,7 +341,7 @@ module ActiveMerchant #:nodoc:
332
341
  post[:deliveryAddress][:stateOrProvince] = get_state(address)
333
342
  post[:deliveryAddress][:country] = address[:country] if address[:country]
334
343
  end
335
- return unless post[:card]&.kind_of?(Hash)
344
+ return unless post[:bankAccount]&.kind_of?(Hash) || post[:card]&.kind_of?(Hash)
336
345
 
337
346
  if (address = options[:billing_address] || options[:address]) && address[:country]
338
347
  post[:billingAddress] = {}
@@ -355,6 +364,7 @@ module ActiveMerchant #:nodoc:
355
364
  value: localized_amount(money, currency),
356
365
  currency: currency
357
366
  }
367
+
358
368
  post[:amount] = amount
359
369
  end
360
370
 
@@ -367,17 +377,32 @@ module ActiveMerchant #:nodoc:
367
377
  post[:modificationAmount] = amount
368
378
  end
369
379
 
370
- def add_payment(post, payment, options)
380
+ def add_payment(post, payment, options, action = nil)
371
381
  if payment.is_a?(String)
372
382
  _, _, recurring_detail_reference = payment.split('#')
373
383
  post[:selectedRecurringDetailReference] = recurring_detail_reference
374
384
  options[:recurring_contract_type] ||= 'RECURRING'
385
+ elsif payment.is_a?(Check)
386
+ add_bank_account(post, payment, options, action)
375
387
  else
376
388
  add_mpi_data_for_network_tokenization_card(post, payment) if payment.is_a?(NetworkTokenizationCreditCard)
377
389
  add_card(post, payment)
378
390
  end
379
391
  end
380
392
 
393
+ def add_bank_account(post, bank_account, options, action)
394
+ bank = {
395
+ bankAccountNumber: bank_account.account_number,
396
+ ownerName: bank_account.name,
397
+ countryCode: options[:billing_address][:country]
398
+ }
399
+
400
+ action == 'refundWithData' ? bank[:iban] = bank_account.routing_number : bank[:bankLocationId] = bank_account.routing_number
401
+
402
+ requires!(bank, :bankAccountNumber, :ownerName, :countryCode)
403
+ post[:bankAccount] = bank
404
+ end
405
+
381
406
  def add_card(post, credit_card)
382
407
  card = {
383
408
  expiryMonth: credit_card.month,
@@ -400,8 +425,10 @@ module ActiveMerchant #:nodoc:
400
425
  end
401
426
 
402
427
  def add_network_transaction_reference(post, options)
428
+ return unless ntid = options[:network_transaction_id] || options.dig(:stored_credential, :network_transaction_id)
429
+
403
430
  post[:additionalData] = {} unless post[:additionalData]
404
- post[:additionalData][:networkTxReference] = options[:network_transaction_id] if options[:network_transaction_id]
431
+ post[:additionalData][:networkTxReference] = ntid
405
432
  end
406
433
 
407
434
  def add_reference(post, authorization, options = {})
@@ -427,6 +454,31 @@ module ActiveMerchant #:nodoc:
427
454
  post[:recurring] = recurring
428
455
  end
429
456
 
457
+ def add_application_info(post, options)
458
+ post[:applicationInfo] ||= {}
459
+ add_external_platform(post, options)
460
+ add_merchant_application(post, options)
461
+ end
462
+
463
+ def add_external_platform(post, options)
464
+ return unless options[:externalPlatform]
465
+
466
+ post[:applicationInfo][:externalPlatform] = {
467
+ name: options[:externalPlatform][:name],
468
+ version: options[:externalPlatform][:version],
469
+ integrator: options[:externalPlatform][:integrator]
470
+ }
471
+ end
472
+
473
+ def add_merchant_application(post, options)
474
+ return unless options[:merchantApplication]
475
+
476
+ post[:applicationInfo][:merchantApplication] = {
477
+ name: options[:merchantApplication][:name],
478
+ version: options[:merchantApplication][:version]
479
+ }
480
+ end
481
+
430
482
  def add_installments(post, options)
431
483
  post[:installments] = {
432
484
  value: options[:installments]
@@ -150,23 +150,13 @@ module ActiveMerchant #:nodoc:
150
150
 
151
151
  def authorize(money, credit_card_or_reference, options = {})
152
152
  post = {}
153
- add_pair(post, :captureDelay, -1)
154
- add_amount(post, money, options)
155
- add_invoice(post, credit_card_or_reference, money, options)
156
- add_credit_card_or_reference(post, credit_card_or_reference)
157
- add_customer_data(post, options)
158
- add_remote_address(post, options)
153
+ add_auth_purchase(post, -1, money, credit_card_or_reference, options)
159
154
  commit('SALE', post)
160
155
  end
161
156
 
162
157
  def purchase(money, credit_card_or_reference, options = {})
163
158
  post = {}
164
- add_pair(post, :captureDelay, 0)
165
- add_amount(post, money, options)
166
- add_invoice(post, credit_card_or_reference, money, options)
167
- add_credit_card_or_reference(post, credit_card_or_reference)
168
- add_customer_data(post, options)
169
- add_remote_address(post, options)
159
+ add_auth_purchase(post, 0, money, credit_card_or_reference, options)
170
160
  commit('SALE', post)
171
161
  end
172
162
 
@@ -184,6 +174,7 @@ module ActiveMerchant #:nodoc:
184
174
  add_pair(post, :xref, authorization)
185
175
  add_amount(post, money, options)
186
176
  add_remote_address(post, options)
177
+ add_country_code(post, options)
187
178
  response = commit('REFUND_SALE', post)
188
179
 
189
180
  return response if response.success?
@@ -223,6 +214,16 @@ module ActiveMerchant #:nodoc:
223
214
 
224
215
  private
225
216
 
217
+ def add_auth_purchase(post, pair_value, money, credit_card_or_reference, options)
218
+ add_pair(post, :captureDelay, pair_value)
219
+ add_amount(post, money, options)
220
+ add_invoice(post, credit_card_or_reference, money, options)
221
+ add_credit_card_or_reference(post, credit_card_or_reference)
222
+ add_customer_data(post, options)
223
+ add_remote_address(post, options)
224
+ add_country_code(post, options)
225
+ end
226
+
226
227
  def add_amount(post, money, options)
227
228
  currency = options[:currency] || currency(money)
228
229
  add_pair(post, :amount, localized_amount(money, currency), required: true)
@@ -286,6 +287,10 @@ module ActiveMerchant #:nodoc:
286
287
  add_pair(post, :remoteAddress, options[:ip] || '1.1.1.1')
287
288
  end
288
289
 
290
+ def add_country_code(post, options)
291
+ post[:countryCode] = options[:country_code] || self.supported_countries[0]
292
+ end
293
+
289
294
  def normalize_line_endings(str)
290
295
  str.gsub(/%0D%0A|%0A%0D|%0D/, '%0A')
291
296
  end
@@ -309,7 +314,6 @@ module ActiveMerchant #:nodoc:
309
314
  end
310
315
 
311
316
  def commit(action, parameters)
312
- parameters.update(countryCode: self.supported_countries[0]) unless %w[CAPTURE CANCEL].include?(action)
313
317
  parameters.update(
314
318
  merchantID: @options[:login],
315
319
  action: action
@@ -41,7 +41,7 @@ module ActiveMerchant #:nodoc:
41
41
  def purchase(money, payment_object, options = {})
42
42
  post = {}
43
43
  add_creditcard(post, payment_object)
44
- add_invoice(post, options)
44
+ add_invoice(post, money, options)
45
45
  add_address(post, options)
46
46
  add_customer_data(post, options)
47
47
  commit('SALE', money, post)
@@ -50,7 +50,7 @@ module ActiveMerchant #:nodoc:
50
50
  def refund(money, identification, options = {})
51
51
  post = {}
52
52
  post[:origtx] = identification
53
- add_invoice(post, options)
53
+ add_invoice(post, money, options)
54
54
  add_customer_data(post, options)
55
55
  commit('REFUND', money, post)
56
56
  end
@@ -69,7 +69,6 @@ module ActiveMerchant #:nodoc:
69
69
  private
70
70
 
71
71
  def commit(action, money, fields)
72
- fields[:amount] = amount(money)
73
72
  url = (test? ? test_url : live_url) + CGI.escape(@options[:merchant_gateway_name])
74
73
  raw_response = ssl_post(url, post_data(action, fields))
75
74
  parsed_response = parse(raw_response)
@@ -92,6 +91,7 @@ module ActiveMerchant #:nodoc:
92
91
 
93
92
  def post_data(action, parameters = {})
94
93
  post = {}
94
+
95
95
  post[:command] = action
96
96
  post[:merchant] = @options[:merchant]
97
97
  post[:operator] = @options[:operator]
@@ -110,9 +110,19 @@ module ActiveMerchant #:nodoc:
110
110
  post[:lname] = creditcard.last_name
111
111
  end
112
112
 
113
- def add_invoice(post, options)
113
+ def add_invoice(post, money, options)
114
114
  post[:order_number] = options[:order_id] if options[:order_id].present?
115
- post[:itemcode] = (options[:item_code] || @options[:default_item_code])
115
+
116
+ if options[:item_codes].present?
117
+ codes_and_amounts = options[:item_codes].transform_keys { |key| key.to_s.delete('_') }
118
+ codes_and_amounts.each do |key, value|
119
+ post[key] = value if key.start_with?('itemcode')
120
+ post[key] = amount(value.to_i) if key.start_with?('amount')
121
+ end
122
+ else
123
+ post[:itemcode] = (options[:item_code] || @options[:default_item_code])
124
+ post[:amount] = amount(money.to_i)
125
+ end
116
126
  end
117
127
 
118
128
  def add_address(post, options)
@@ -87,6 +87,8 @@ module ActiveMerchant #:nodoc:
87
87
  add_transaction_data(post, options)
88
88
  add_3ds(post, options)
89
89
  add_metadata(post, options)
90
+ add_processing_channel(post, options)
91
+ add_marketplace_data(post, options)
90
92
  end
91
93
 
92
94
  def add_invoice(post, money, options)
@@ -109,12 +111,17 @@ module ActiveMerchant #:nodoc:
109
111
 
110
112
  def add_payment_method(post, payment_method, options)
111
113
  post[:source] = {}
112
- if payment_method.is_a?(NetworkTokenizationCreditCard) && payment_method.source == :network_token
114
+ if payment_method.is_a?(NetworkTokenizationCreditCard)
115
+ token_type = token_type_from(payment_method)
116
+ cryptogram = payment_method.payment_cryptogram
117
+ eci = payment_method.eci || options[:eci]
118
+ eci ||= '05' if token_type == 'vts'
119
+
113
120
  post[:source][:type] = 'network_token'
114
121
  post[:source][:token] = payment_method.number
115
- post[:source][:token_type] = payment_method.brand == 'visa' ? 'vts' : 'mdes'
116
- post[:source][:cryptogram] = payment_method.payment_cryptogram
117
- post[:source][:eci] = options[:eci] || '05'
122
+ post[:source][:token_type] = token_type
123
+ post[:source][:cryptogram] = cryptogram if cryptogram
124
+ post[:source][:eci] = eci if eci
118
125
  else
119
126
  post[:source][:type] = 'card'
120
127
  post[:source][:name] = payment_method.name
@@ -186,6 +193,17 @@ module ActiveMerchant #:nodoc:
186
193
  end
187
194
  end
188
195
 
196
+ def add_processing_channel(post, options)
197
+ post[:processing_channel_id] = options[:processing_channel_id] if options[:processing_channel_id]
198
+ end
199
+
200
+ def add_marketplace_data(post, options)
201
+ if options[:marketplace]
202
+ post[:marketplace] = {}
203
+ post[:marketplace][:sub_entity_id] = options[:marketplace][:sub_entity_id] if options[:marketplace][:sub_entity_id]
204
+ end
205
+ end
206
+
189
207
  def commit(action, post, authorization = nil)
190
208
  begin
191
209
  raw_response = (action == :verify_payment ? ssl_get("#{base_url}/payments/#{post}", headers) : ssl_post(url(post, action, authorization), post.to_json, headers))
@@ -306,6 +324,17 @@ module ActiveMerchant #:nodoc:
306
324
  STANDARD_ERROR_CODE_MAPPING[response['response_code']]
307
325
  end
308
326
  end
327
+
328
+ def token_type_from(payment_method)
329
+ case payment_method.source
330
+ when :network_token
331
+ payment_method.brand == 'visa' ? 'vts' : 'mdes'
332
+ when :google_pay, :android_pay
333
+ 'googlepay'
334
+ when :apple_pay
335
+ 'applepay'
336
+ end
337
+ end
309
338
  end
310
339
  end
311
340
  end
@@ -500,6 +500,8 @@ module ActiveMerchant #:nodoc:
500
500
  end
501
501
 
502
502
  def add_line_item_data(xml, options)
503
+ return unless options[:line_items]
504
+
503
505
  options[:line_items].each_with_index do |value, index|
504
506
  xml.tag! 'item', { 'id' => index } do
505
507
  xml.tag! 'unitPrice', localized_amount(value[:declared_value].to_i, options[:currency] || default_currency)
@@ -507,6 +509,8 @@ module ActiveMerchant #:nodoc:
507
509
  xml.tag! 'productCode', value[:code] || 'shipping_only'
508
510
  xml.tag! 'productName', value[:description]
509
511
  xml.tag! 'productSKU', value[:sku]
512
+ xml.tag! 'taxAmount', value[:tax_amount] if value[:tax_amount]
513
+ xml.tag! 'nationalTax', value[:national_tax] if value[:national_tax]
510
514
  end
511
515
  end
512
516
  end
@@ -522,10 +526,12 @@ module ActiveMerchant #:nodoc:
522
526
  end
523
527
 
524
528
  def add_merchant_descriptor(xml, options)
525
- return unless options[:merchant_descriptor]
529
+ return unless options[:merchant_descriptor] || options[:user_po] || options[:taxable]
526
530
 
527
531
  xml.tag! 'invoiceHeader' do
528
- xml.tag! 'merchantDescriptor', options[:merchant_descriptor]
532
+ xml.tag! 'merchantDescriptor', options[:merchant_descriptor] if options[:merchant_descriptor]
533
+ xml.tag! 'userPO', options[:user_po] if options[:user_po]
534
+ xml.tag! 'taxable', options[:taxable] if options[:taxable]
529
535
  end
530
536
  end
531
537
 
@@ -628,11 +634,12 @@ module ActiveMerchant #:nodoc:
628
634
  end
629
635
 
630
636
  def add_other_tax(xml, options)
631
- return unless options[:local_tax_amount] || options[:national_tax_amount]
637
+ return unless options[:local_tax_amount] || options[:national_tax_amount] || options[:national_tax_indicator]
632
638
 
633
639
  xml.tag! 'otherTax' do
634
640
  xml.tag! 'localTaxAmount', options[:local_tax_amount] if options[:local_tax_amount]
635
641
  xml.tag! 'nationalTaxAmount', options[:national_tax_amount] if options[:national_tax_amount]
642
+ xml.tag! 'nationalTaxIndicator', options[:national_tax_indicator] if options[:national_tax_indicator]
636
643
  end
637
644
  end
638
645
 
@@ -887,6 +894,7 @@ module ActiveMerchant #:nodoc:
887
894
  else
888
895
  add_address(xml, payment_method_or_reference, options[:billing_address], options)
889
896
  add_address(xml, payment_method_or_reference, options[:shipping_address], options, true)
897
+ add_line_item_data(xml, options)
890
898
  add_purchase_data(xml, money, true, options)
891
899
  add_installments(xml, options)
892
900
  add_creditcard(xml, payment_method_or_reference)