activemerchant 1.119.0 → 1.120.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +4 -4
- data/CHANGELOG +75 -1
- data/README.md +3 -1
- data/lib/active_merchant/billing/check.rb +10 -0
- data/lib/active_merchant/billing/credit_card_methods.rb +9 -3
- data/lib/active_merchant/billing/gateways/adyen.rb +20 -6
- data/lib/active_merchant/billing/gateways/authorize_net.rb +9 -3
- data/lib/active_merchant/billing/gateways/authorize_net_cim.rb +3 -0
- data/lib/active_merchant/billing/gateways/braintree_blue.rb +47 -7
- data/lib/active_merchant/billing/gateways/cashnet.rb +7 -2
- data/lib/active_merchant/billing/gateways/checkout_v2.rb +21 -0
- data/lib/active_merchant/billing/gateways/credorax.rb +13 -8
- data/lib/active_merchant/billing/gateways/cyber_source.rb +23 -3
- data/lib/active_merchant/billing/gateways/d_local.rb +1 -1
- data/lib/active_merchant/billing/gateways/elavon.rb +11 -1
- data/lib/active_merchant/billing/gateways/forte.rb +12 -0
- data/lib/active_merchant/billing/gateways/hps.rb +55 -1
- data/lib/active_merchant/billing/gateways/litle.rb +1 -1
- data/lib/active_merchant/billing/gateways/mercado_pago.rb +2 -2
- data/lib/active_merchant/billing/gateways/netbanx.rb +26 -2
- data/lib/active_merchant/billing/gateways/orbital.rb +62 -53
- data/lib/active_merchant/billing/gateways/payeezy.rb +30 -6
- data/lib/active_merchant/billing/gateways/payment_express.rb +5 -5
- data/lib/active_merchant/billing/gateways/payway_dot_com.rb +253 -0
- data/lib/active_merchant/billing/gateways/qvalent.rb +23 -9
- data/lib/active_merchant/billing/gateways/redsys.rb +19 -4
- data/lib/active_merchant/billing/gateways/safe_charge.rb +18 -11
- data/lib/active_merchant/billing/gateways/stripe.rb +8 -8
- data/lib/active_merchant/billing/gateways/stripe_payment_intents.rb +61 -25
- data/lib/active_merchant/billing/gateways/vpos.rb +172 -0
- data/lib/active_merchant/billing/gateways/worldpay.rb +24 -11
- data/lib/active_merchant/version.rb +1 -1
- data/lib/certs/cacert.pem +1582 -2431
- metadata +5 -3
checksums.yaml
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
---
|
|
2
2
|
SHA256:
|
|
3
|
-
metadata.gz:
|
|
4
|
-
data.tar.gz:
|
|
3
|
+
metadata.gz: 649ffe0485eeee7fba63fb57ee6f2ccee8ae113d8ad7ec42fb26d7895f5e8c03
|
|
4
|
+
data.tar.gz: 24dcf747601a2be45ca1938919e0626428be6ea19a22834666166772c8773035
|
|
5
5
|
SHA512:
|
|
6
|
-
metadata.gz:
|
|
7
|
-
data.tar.gz:
|
|
6
|
+
metadata.gz: 72e799731ef457d0f5c9d9995591c692e268265562465ba91023e87dad7fde4b25db3754920a51e24180d052d59ce7ecc33a7b2f2fc80b1e127984c5550122f9
|
|
7
|
+
data.tar.gz: 6dcc6c4f22b351497233ebd2ef9fc6354113921c75a4279909050e73e509570d6d97b698c9aa98199b7996019a53fb4dbb2daaa8ba1f85732d0af748033022ff
|
data/CHANGELOG
CHANGED
|
@@ -2,11 +2,84 @@
|
|
|
2
2
|
|
|
3
3
|
== HEAD
|
|
4
4
|
|
|
5
|
+
|
|
6
|
+
== Version 1.120.0 (May 28th, 2021)
|
|
7
|
+
* Braintree: Bump required braintree gem version to 3.0.1
|
|
8
|
+
* Stripe PI: ensure `setup_future_sage` and `off_session` work when using SetupIntents.
|
|
9
|
+
* Orbital: Update commit to accept retry_logic in params [jessiagee] #3890
|
|
10
|
+
* Orbital: Update remote 3DS tests [jessiagee] #3892
|
|
11
|
+
* Mercado Pago: support Creditel card type [therufs] #3893
|
|
12
|
+
* Payeezy: Update error mapping [meagabeth] #3896
|
|
13
|
+
* HPS: Add support for stored_credential [cdmackeyfree] #3894
|
|
14
|
+
* Orbital: Ensure payment_detail sends for ECP [jessiagee] #3899
|
|
15
|
+
* Payeezy: Update `error_code_from` method [meagabeth] #3900
|
|
16
|
+
* Worldpay: Add support for `statementNarrative` field [meagabeth] #3901
|
|
17
|
+
* Mercado Pago: Give ability to pass capture option in authorize txn field [naashton] #3897
|
|
18
|
+
* Orbital: Ensure correct fields sent in refund [jessiagee] #3903
|
|
19
|
+
* WorldPay: remove some defaults in billing address [carrigan] #3902
|
|
20
|
+
* Adyen: Support for General Credit [naashton] #3904
|
|
21
|
+
* Worldpay: reintroduce address1 and city defaults [carrigan] #3905
|
|
22
|
+
* Stripe: ensure potentially nested data is scrubbed #3907
|
|
23
|
+
* Stripe PI: Send Validate on Payment Method Attach [tatsianaclifton] #3909
|
|
24
|
+
* Adyen: Update handling of authorization returned from gateway [meagabeth] #3910
|
|
25
|
+
* Update gateway templates for Rubocop compliance [therufs] #3912 #3895
|
|
26
|
+
* Orbital: Send AVSname for all eCheck transactions [jessiagee] #3911
|
|
27
|
+
* Litle: update support of customerId field [cdmackeyfree] #3913
|
|
28
|
+
* Payment Express: fix signature for `verify` [therufs] #3914
|
|
29
|
+
* Forte: Send xdata fields [dsmcclain] #3915
|
|
30
|
+
* PaywayDotCom: Add New Gateway [DanAtPayway] #3898
|
|
31
|
+
* Orbital: Remove unnecessary requirements [jessiagee] #3917
|
|
32
|
+
* SafeCharge (Nuvei): Add network tokenization support [DStoyanoff] #3847
|
|
33
|
+
* Stripe PI: Enhance testing of SetupIntents API #3908
|
|
34
|
+
* SafeCharge (Nuvei): Fix NT related bug [jimilpatel24] #3921
|
|
35
|
+
* Worldpay: Only override cardholdername for 3ds tests [curiousepic] #3918
|
|
36
|
+
* Orbital: Add support for general credit [meagabeth] #3922
|
|
37
|
+
* Banco Sabadell: Ensure sca_exemption field is used #3923
|
|
38
|
+
* Redsys: Refactor XML character escape logic #3925
|
|
39
|
+
* HPS: Strip zip codes of non-alphanumeric characters [dsmcclain] #3926
|
|
40
|
+
* Orbital: $0 PreNote using authorize for eCheck force_capture [jessiagee] #3927
|
|
41
|
+
* Worldpay: synchronous response changes [naashton] #3928
|
|
42
|
+
* PaywayDotCom: Add more thorough scrubbing [tatsianaclifton] #3929
|
|
43
|
+
* Remove CONTRIBUTING.md and update README.md to reflect new repository wiki [dsmcclain] #3930
|
|
44
|
+
* Qvalent: Add customer_reference_number [fredo-] #3931
|
|
45
|
+
* Orbital: Add 'ND' ECPActionCode to $0 Prenote Check [jessiagee] #3935
|
|
46
|
+
* Checkout: Add support for stored_credential [meagabeth] #3934
|
|
47
|
+
* Credorax: Add support for 3ds_reqchallengeind [dsmcclain] #3936
|
|
48
|
+
* Adyen: cancelOrRefund endpoint when passed as option [naashton] #3937
|
|
49
|
+
* Qvalent: Add customer reference number FIX [fredo-] #3939
|
|
50
|
+
* Orbital: Pass line_items in capture [jessiagee] #3941
|
|
51
|
+
* BraintreeBlue: Add support for $0 auth verification [meagabeth] #3944
|
|
52
|
+
* JCB: Add additional BIN ranges [dsmcclain] #3946
|
|
53
|
+
* vPOS: Support new gateway type [therufs] #3906
|
|
54
|
+
* Braintree: Add support for AVS and CVV results in $0 credit card verification transactions [meagabeth] #3951
|
|
55
|
+
* Braintree: Return cvv_code and avs_code in response [meagabeth] #3952
|
|
56
|
+
* vPOS: Stringify values [therufs] #3954
|
|
57
|
+
* Payeezy: Send level2 fields [dsmcclain] #3953
|
|
58
|
+
* Credorax: adjust logic for sending 3ds shipping address fields [dsmcclain] #3959
|
|
59
|
+
* Orbital: Ensure ECP always sends AVSName [jessiagee] #3963
|
|
60
|
+
* Orbital: Add middle name to EWSMiddleName for ECP [jessiagee] #3962
|
|
61
|
+
* Support Canadian Bank Accounts [naashton] #3964
|
|
62
|
+
* Windcave/Payment Express: Add support for AvsAction and EnableAVSData fields [meagabeth] #3967
|
|
63
|
+
* CyberSource: Update XML tag for merchantDefinedData [meagabeth] #3969
|
|
64
|
+
* Elavon: Send ssl_vendor_id field [dsmcclain] #3972
|
|
65
|
+
* Credorax: Add support for `echo` field [meagabeth] #3973
|
|
66
|
+
* Worldpay: support cancelOrRefund via options [therufs] #3975
|
|
67
|
+
* Payeezy: support general credit [cdmackeyfree] #3977
|
|
68
|
+
* Ripley and Hipercard: Add BIN ranges [naashton] #3978
|
|
69
|
+
* Adyen: Default card holder name for credit cards [shasum] #3980
|
|
70
|
+
* PaywayDotCom: make `source_id` a required field [dsmcclain] # 3981
|
|
71
|
+
* Qvalent: remove `pem_password` from required credentials [dsmcclain] #3982
|
|
72
|
+
* Authorize.net: Fix stored credentials [tatsianaclifton] #3971
|
|
73
|
+
* CyberSource: Add support for multiple new fields [dsmcclain] #3984
|
|
74
|
+
* CASHNet: Update gateway adapter [dsmcclain] #3986
|
|
75
|
+
* Elavon: Send `ssl_vendor_id` field via options on gateway initialization [dsmcclain] #3989
|
|
76
|
+
|
|
5
77
|
== Version 1.119.0 (February 9th, 2021)
|
|
6
78
|
* Payment Express: support verify/validate [therufs] #3874
|
|
7
79
|
* GlobalCollect: Truncate address fields [meagabeth] #3878
|
|
8
80
|
* Litle: Truncate address fields [meagabeth] #3877
|
|
9
81
|
* Netbanx: Add-customer-information(name,email,IP)-to-a-transaction [rockyhakjoong] #3754
|
|
82
|
+
* Netbanx: Adjust the avs and cvv return code in shopify [rockyhakjoong] #3833
|
|
10
83
|
* Decidir: Improve error mapping [meagabeth] #3875
|
|
11
84
|
* Worldpay: support `skip_capture` [therufs] #3879
|
|
12
85
|
* Redsys: Add new response code text [britth] #3880
|
|
@@ -15,8 +88,9 @@
|
|
|
15
88
|
* HPS: Update Add support for general credit [naashton] #3885
|
|
16
89
|
* Elavon: Fix issue with encoding data sent in the request [naashton] #3865
|
|
17
90
|
* Orbital: Update ECP to use EWS verification [jessiagee] #3886
|
|
18
|
-
* Eway: Add 3ds field when do direct payment [GavinSun9527] #3860
|
|
91
|
+
* Eway: Add 3ds field when do direct payment [GavinSun9527] #3860
|
|
19
92
|
* Support Creditel cardtype [therufs] #3883
|
|
93
|
+
* Elavon: Remove ampersand char from fields [naashton] #3891
|
|
20
94
|
|
|
21
95
|
== Version 1.118.0 (January 22nd, 2021)
|
|
22
96
|
* Worldpay: Add support for challengeWindowSize [carrigan] #3823
|
data/README.md
CHANGED
|
@@ -17,7 +17,7 @@ from an ever-growing set of contributors.
|
|
|
17
17
|
See [GettingStarted.md](GettingStarted.md) if you want to learn more about using Active Merchant in your
|
|
18
18
|
applications.
|
|
19
19
|
|
|
20
|
-
If you'd like to contribute to Active Merchant, please start with our [
|
|
20
|
+
If you'd like to contribute to Active Merchant, please start with our [Contribution Guide](https://github.com/activemerchant/active_merchant/wiki/Contributing).
|
|
21
21
|
|
|
22
22
|
## Installation
|
|
23
23
|
|
|
@@ -81,6 +81,8 @@ if credit_card.validate.empty?
|
|
|
81
81
|
end
|
|
82
82
|
```
|
|
83
83
|
|
|
84
|
+
## Contributing
|
|
85
|
+
|
|
84
86
|
For more in-depth documentation and tutorials, see [GettingStarted.md](GettingStarted.md) and the
|
|
85
87
|
[API documentation](http://www.rubydoc.info/github/activemerchant/active_merchant/).
|
|
86
88
|
|
|
@@ -13,6 +13,14 @@ module ActiveMerchant #:nodoc:
|
|
|
13
13
|
# Used for Canadian bank accounts
|
|
14
14
|
attr_accessor :institution_number, :transit_number
|
|
15
15
|
|
|
16
|
+
# Canadian Institution Numbers
|
|
17
|
+
# Found here: https://en.wikipedia.org/wiki/Routing_number_(Canada)
|
|
18
|
+
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
|
|
21
|
+
865 879 889 899
|
|
22
|
+
)
|
|
23
|
+
|
|
16
24
|
def name
|
|
17
25
|
@name ||= "#{first_name} #{last_name}".strip
|
|
18
26
|
end
|
|
@@ -67,6 +75,8 @@ module ActiveMerchant #:nodoc:
|
|
|
67
75
|
else
|
|
68
76
|
false
|
|
69
77
|
end
|
|
78
|
+
when 8
|
|
79
|
+
true if INSTITUTION_NUMBERS.include?(routing_number[0..2].to_s)
|
|
70
80
|
else
|
|
71
81
|
false
|
|
72
82
|
end
|
|
@@ -11,7 +11,7 @@ module ActiveMerchant #:nodoc:
|
|
|
11
11
|
'american_express' => ->(num) { num =~ /^3[47]\d{13}$/ },
|
|
12
12
|
'naranja' => ->(num) { num&.size == 16 && in_bin_range?(num.slice(0, 6), NARANJA_RANGES) },
|
|
13
13
|
'diners_club' => ->(num) { num =~ /^3(0[0-5]|[68]\d)\d{11,16}$/ },
|
|
14
|
-
'jcb' => ->(num) { num =~ /^35(28|29|[3-8]\d)\d{12}$/ },
|
|
14
|
+
'jcb' => ->(num) { num =~ /^(35(28|29|[3-8]\d)\d{12}|308800\d{10})$/ },
|
|
15
15
|
'dankort' => ->(num) { num =~ /^5019\d{12}$/ },
|
|
16
16
|
'maestro' => lambda { |num|
|
|
17
17
|
(12..19).cover?(num&.size) && (
|
|
@@ -71,6 +71,12 @@ module ActiveMerchant #:nodoc:
|
|
|
71
71
|
MASTERCARD_RANGES = [
|
|
72
72
|
(222100..272099),
|
|
73
73
|
(510000..559999),
|
|
74
|
+
[605272],
|
|
75
|
+
[606282],
|
|
76
|
+
[637095],
|
|
77
|
+
[637568],
|
|
78
|
+
(637599..637600),
|
|
79
|
+
[637609],
|
|
74
80
|
]
|
|
75
81
|
|
|
76
82
|
MAESTRO_BINS = Set.new(
|
|
@@ -105,7 +111,7 @@ module ActiveMerchant #:nodoc:
|
|
|
105
111
|
606126
|
|
106
112
|
636380 636422 636502 636639
|
|
107
113
|
637046 637756
|
|
108
|
-
639130
|
|
114
|
+
639130 639229
|
|
109
115
|
690032]
|
|
110
116
|
)
|
|
111
117
|
|
|
@@ -198,7 +204,7 @@ module ActiveMerchant #:nodoc:
|
|
|
198
204
|
def self.in_bin_range?(number, ranges)
|
|
199
205
|
bin = number.to_i
|
|
200
206
|
ranges.any? do |range|
|
|
201
|
-
range.
|
|
207
|
+
range.include?(bin)
|
|
202
208
|
end
|
|
203
209
|
end
|
|
204
210
|
|
|
@@ -78,10 +78,19 @@ module ActiveMerchant #:nodoc:
|
|
|
78
78
|
commit('refund', post, options)
|
|
79
79
|
end
|
|
80
80
|
|
|
81
|
+
def credit(money, payment, options = {})
|
|
82
|
+
post = init_post(options)
|
|
83
|
+
add_invoice(post, money, options)
|
|
84
|
+
add_payment(post, payment, options)
|
|
85
|
+
add_shopper_reference(post, options)
|
|
86
|
+
commit('refundWithData', post, options)
|
|
87
|
+
end
|
|
88
|
+
|
|
81
89
|
def void(authorization, options = {})
|
|
82
90
|
post = init_post(options)
|
|
91
|
+
endpoint = options[:cancel_or_refund] ? 'cancelOrRefund' : 'cancel'
|
|
83
92
|
add_reference(post, authorization, options)
|
|
84
|
-
commit(
|
|
93
|
+
commit(endpoint, post, options)
|
|
85
94
|
end
|
|
86
95
|
|
|
87
96
|
def adjust(money, authorization, options = {})
|
|
@@ -374,7 +383,7 @@ module ActiveMerchant #:nodoc:
|
|
|
374
383
|
}
|
|
375
384
|
|
|
376
385
|
card.delete_if { |_k, v| v.blank? }
|
|
377
|
-
card[:holderName] ||= 'Not Provided'
|
|
386
|
+
card[:holderName] ||= 'Not Provided'
|
|
378
387
|
requires!(card, :expiryMonth, :expiryYear, :holderName, :number)
|
|
379
388
|
post[:card] = card
|
|
380
389
|
end
|
|
@@ -391,7 +400,11 @@ module ActiveMerchant #:nodoc:
|
|
|
391
400
|
end
|
|
392
401
|
|
|
393
402
|
def add_original_reference(post, authorization, options = {})
|
|
394
|
-
|
|
403
|
+
if authorization.start_with?('#')
|
|
404
|
+
_, original_psp_reference, = authorization.split('#')
|
|
405
|
+
else
|
|
406
|
+
original_psp_reference, = authorization.split('#')
|
|
407
|
+
end
|
|
395
408
|
post[:originalReference] = single_reference(authorization) || original_psp_reference
|
|
396
409
|
end
|
|
397
410
|
|
|
@@ -552,11 +565,10 @@ module ActiveMerchant #:nodoc:
|
|
|
552
565
|
response['refusalReason'] = 'Received unexpected 3DS authentication response. Use the execute_threed and/or threed_dynamic options to initiate a proper 3DS flow.'
|
|
553
566
|
return false
|
|
554
567
|
end
|
|
555
|
-
|
|
556
568
|
case action.to_s
|
|
557
569
|
when 'authorise', 'authorise3d'
|
|
558
570
|
%w[Authorised Received RedirectShopper].include?(response['resultCode'])
|
|
559
|
-
when 'capture', 'refund', 'cancel'
|
|
571
|
+
when 'capture', 'refund', 'cancel', 'cancelOrRefund'
|
|
560
572
|
response['response'] == "[#{action}-received]"
|
|
561
573
|
when 'adjustAuthorisation'
|
|
562
574
|
response['response'] == 'Authorised' || response['response'] == '[adjustAuthorisation-received]'
|
|
@@ -564,6 +576,8 @@ module ActiveMerchant #:nodoc:
|
|
|
564
576
|
response['result'] == 'Success'
|
|
565
577
|
when 'disable'
|
|
566
578
|
response['response'] == '[detail-successfully-disabled]'
|
|
579
|
+
when 'refundWithData'
|
|
580
|
+
response['resultCode'] == 'Received'
|
|
567
581
|
else
|
|
568
582
|
false
|
|
569
583
|
end
|
|
@@ -572,7 +586,7 @@ module ActiveMerchant #:nodoc:
|
|
|
572
586
|
def message_from(action, response)
|
|
573
587
|
return authorize_message_from(response) if %w(authorise authorise3d authorise3ds2).include?(action.to_s)
|
|
574
588
|
|
|
575
|
-
response['response'] || response['message'] || response['result']
|
|
589
|
+
response['response'] || response['message'] || response['result'] || response['resultCode']
|
|
576
590
|
end
|
|
577
591
|
|
|
578
592
|
def authorize_message_from(response)
|
|
@@ -708,9 +708,10 @@ module ActiveMerchant
|
|
|
708
708
|
return unless options[:stored_credential]
|
|
709
709
|
|
|
710
710
|
xml.processingOptions do
|
|
711
|
-
if options[:stored_credential][:initial_transaction]
|
|
711
|
+
if options[:stored_credential][:initial_transaction] && options[:stored_credential][:reason_type] == 'recurring'
|
|
712
|
+
xml.isFirstRecurringPayment 'true'
|
|
713
|
+
elsif options[:stored_credential][:initial_transaction]
|
|
712
714
|
xml.isFirstSubsequentAuth 'true'
|
|
713
|
-
# xml.isFirstRecurringPayment 'true' if options[:stored_credential][:reason_type] == 'recurring'
|
|
714
715
|
elsif options[:stored_credential][:initiator] == 'cardholder'
|
|
715
716
|
xml.isStoredCredentials 'true'
|
|
716
717
|
else
|
|
@@ -720,7 +721,7 @@ module ActiveMerchant
|
|
|
720
721
|
end
|
|
721
722
|
|
|
722
723
|
def add_subsequent_auth_information(xml, options)
|
|
723
|
-
return unless options.dig(:stored_credential, :
|
|
724
|
+
return unless options.dig(:stored_credential, :initiator) == 'merchant'
|
|
724
725
|
|
|
725
726
|
xml.subsequentAuthInformation do
|
|
726
727
|
xml.reason options[:stored_credential_reason_type_override] if options[:stored_credential_reason_type_override]
|
|
@@ -934,6 +935,11 @@ module ActiveMerchant
|
|
|
934
935
|
empty?(element.content) ? nil : element.content
|
|
935
936
|
end
|
|
936
937
|
|
|
938
|
+
response[:network_trans_id] =
|
|
939
|
+
if element = doc.at_xpath('//networkTransId')
|
|
940
|
+
empty?(element.content) ? nil : element.content
|
|
941
|
+
end
|
|
942
|
+
|
|
937
943
|
response
|
|
938
944
|
end
|
|
939
945
|
|
|
@@ -563,6 +563,8 @@ module ActiveMerchant #:nodoc:
|
|
|
563
563
|
|
|
564
564
|
def build_get_customer_profile_request(xml, options)
|
|
565
565
|
xml.tag!('customerProfileId', options[:customer_profile_id])
|
|
566
|
+
xml.tag!('unmaskExpirationDate', options[:unmask_expiration_date]) if options[:unmask_expiration_date]
|
|
567
|
+
xml.tag!('includeIssuerInfo', options[:include_issuer_info]) if options[:include_issuer_info]
|
|
566
568
|
xml.target!
|
|
567
569
|
end
|
|
568
570
|
|
|
@@ -574,6 +576,7 @@ module ActiveMerchant #:nodoc:
|
|
|
574
576
|
xml.tag!('customerProfileId', options[:customer_profile_id])
|
|
575
577
|
xml.tag!('customerPaymentProfileId', options[:customer_payment_profile_id])
|
|
576
578
|
xml.tag!('unmaskExpirationDate', options[:unmask_expiration_date]) if options[:unmask_expiration_date]
|
|
579
|
+
xml.tag!('includeIssuerInfo', options[:include_issuer_info]) if options[:include_issuer_info]
|
|
577
580
|
xml.target!
|
|
578
581
|
end
|
|
579
582
|
|
|
@@ -7,7 +7,7 @@ rescue LoadError
|
|
|
7
7
|
raise 'Could not load the braintree gem. Use `gem install braintree` to install it.'
|
|
8
8
|
end
|
|
9
9
|
|
|
10
|
-
raise "Need braintree gem >=
|
|
10
|
+
raise "Need braintree gem >= 3.0.0. Run `gem install braintree --version '~>3.0.0'` to get the correct version." unless Braintree::Version::Major == 3 && Braintree::Version::Minor == 0
|
|
11
11
|
|
|
12
12
|
module ActiveMerchant #:nodoc:
|
|
13
13
|
module Billing #:nodoc:
|
|
@@ -115,10 +115,36 @@ module ActiveMerchant #:nodoc:
|
|
|
115
115
|
end
|
|
116
116
|
end
|
|
117
117
|
|
|
118
|
-
def verify(
|
|
119
|
-
|
|
120
|
-
|
|
121
|
-
|
|
118
|
+
def verify(creditcard, options = {})
|
|
119
|
+
if options[:allow_card_verification] == true
|
|
120
|
+
options.delete(:allow_card_verification)
|
|
121
|
+
exp_month = creditcard.month.to_s
|
|
122
|
+
exp_year = creditcard.year.to_s
|
|
123
|
+
expiration = "#{exp_month}/#{exp_year}"
|
|
124
|
+
payload = {
|
|
125
|
+
credit_card: {
|
|
126
|
+
number: creditcard.number,
|
|
127
|
+
expiration_date: expiration,
|
|
128
|
+
cvv: creditcard.verification_value,
|
|
129
|
+
billing_address: {
|
|
130
|
+
postal_code: options[:billing_address][:zip]
|
|
131
|
+
}
|
|
132
|
+
}
|
|
133
|
+
}
|
|
134
|
+
commit do
|
|
135
|
+
result = @braintree_gateway.verification.create(payload)
|
|
136
|
+
response = Response.new(result.success?, message_from_transaction_result(result), response_options(result))
|
|
137
|
+
response.cvv_result['message'] = ''
|
|
138
|
+
response.cvv_result['code'] = response.params['cvv_result']
|
|
139
|
+
response.avs_result['code'] = response.params['avs_result'][:code]
|
|
140
|
+
response
|
|
141
|
+
end
|
|
142
|
+
|
|
143
|
+
else
|
|
144
|
+
MultiResponse.run(:use_first_response) do |r|
|
|
145
|
+
r.process { authorize(100, creditcard, options) }
|
|
146
|
+
r.process(:ignore_result) { void(r.authorization, options) }
|
|
147
|
+
end
|
|
122
148
|
end
|
|
123
149
|
end
|
|
124
150
|
|
|
@@ -368,7 +394,11 @@ module ActiveMerchant #:nodoc:
|
|
|
368
394
|
|
|
369
395
|
def response_options(result)
|
|
370
396
|
options = {}
|
|
371
|
-
if result.
|
|
397
|
+
if result.credit_card_verification
|
|
398
|
+
options[:authorization] = result.credit_card_verification.id
|
|
399
|
+
options[:avs_result] = { code: avs_code_from(result.credit_card_verification) }
|
|
400
|
+
options[:cvv_result] = result.credit_card_verification.cvv_response_code
|
|
401
|
+
elsif result.transaction
|
|
372
402
|
options[:authorization] = result.transaction.id
|
|
373
403
|
options[:avs_result] = { code: avs_code_from(result.transaction) }
|
|
374
404
|
options[:cvv_result] = result.transaction.cvv_response_code
|
|
@@ -592,6 +622,7 @@ module ActiveMerchant #:nodoc:
|
|
|
592
622
|
add_addresses(parameters, options)
|
|
593
623
|
|
|
594
624
|
add_descriptor(parameters, options)
|
|
625
|
+
add_risk_data(parameters, options)
|
|
595
626
|
add_travel_data(parameters, options) if options[:travel_data]
|
|
596
627
|
add_lodging_data(parameters, options) if options[:lodging_data]
|
|
597
628
|
add_channel(parameters, options)
|
|
@@ -652,6 +683,15 @@ module ActiveMerchant #:nodoc:
|
|
|
652
683
|
}
|
|
653
684
|
end
|
|
654
685
|
|
|
686
|
+
def add_risk_data(parameters, options)
|
|
687
|
+
return unless options[:risk_data]
|
|
688
|
+
|
|
689
|
+
parameters[:risk_data] = {
|
|
690
|
+
customer_browser: options[:risk_data][:customer_browser],
|
|
691
|
+
customer_ip: options[:risk_data][:customer_ip]
|
|
692
|
+
}
|
|
693
|
+
end
|
|
694
|
+
|
|
655
695
|
def add_level_2_data(parameters, options)
|
|
656
696
|
parameters[:tax_amount] = options[:tax_amount] if options[:tax_amount]
|
|
657
697
|
parameters[:tax_exempt] = options[:tax_exempt] if options[:tax_exempt]
|
|
@@ -761,7 +801,7 @@ module ActiveMerchant #:nodoc:
|
|
|
761
801
|
eci_indicator: credit_card_or_vault_id.eci
|
|
762
802
|
}
|
|
763
803
|
elsif credit_card_or_vault_id.source == :android_pay || credit_card_or_vault_id.source == :google_pay
|
|
764
|
-
parameters[:
|
|
804
|
+
parameters[:google_pay_card] = {
|
|
765
805
|
number: credit_card_or_vault_id.number,
|
|
766
806
|
cryptogram: credit_card_or_vault_id.payment_cryptogram,
|
|
767
807
|
expiration_month: credit_card_or_vault_id.month.to_s.rjust(2, '0'),
|
|
@@ -8,7 +8,7 @@ module ActiveMerchant #:nodoc:
|
|
|
8
8
|
|
|
9
9
|
self.supported_countries = ['US']
|
|
10
10
|
self.supported_cardtypes = %i[visa master american_express discover diners_club jcb]
|
|
11
|
-
self.homepage_url = '
|
|
11
|
+
self.homepage_url = 'https://transactcampus.com'
|
|
12
12
|
self.display_name = 'Cashnet'
|
|
13
13
|
self.money_format = :dollars
|
|
14
14
|
self.max_retries = 0
|
|
@@ -76,7 +76,7 @@ module ActiveMerchant #:nodoc:
|
|
|
76
76
|
|
|
77
77
|
return unparsable_response(raw_response) unless parsed_response
|
|
78
78
|
|
|
79
|
-
success = (parsed_response
|
|
79
|
+
success = success?(parsed_response)
|
|
80
80
|
Response.new(
|
|
81
81
|
success,
|
|
82
82
|
CASHNET_CODES[parsed_response[:result]],
|
|
@@ -86,6 +86,10 @@ module ActiveMerchant #:nodoc:
|
|
|
86
86
|
)
|
|
87
87
|
end
|
|
88
88
|
|
|
89
|
+
def success?(response)
|
|
90
|
+
response[:result] == '0'
|
|
91
|
+
end
|
|
92
|
+
|
|
89
93
|
def post_data(action, parameters = {})
|
|
90
94
|
post = {}
|
|
91
95
|
post[:command] = action
|
|
@@ -191,6 +195,7 @@ module ActiveMerchant #:nodoc:
|
|
|
191
195
|
'215' => 'Old PIN does not validate ',
|
|
192
196
|
'221' => 'Invalid credit card processor type specified in location or payment code',
|
|
193
197
|
'222' => 'Credit card processor error',
|
|
198
|
+
'230' => 'Host Error (USE VOID OR REVERSAL TO REFUND UNSETTLED TRANSACTIONS)',
|
|
194
199
|
'280' => 'SmartPay transaction not posted',
|
|
195
200
|
'301' => 'Original transaction not found for this customer',
|
|
196
201
|
'302' => 'Amount to refund exceeds original payment amount or is missing',
|
|
@@ -79,6 +79,7 @@ module ActiveMerchant #:nodoc:
|
|
|
79
79
|
add_invoice(post, amount, options)
|
|
80
80
|
add_payment_method(post, payment_method, options)
|
|
81
81
|
add_customer_data(post, options)
|
|
82
|
+
add_stored_credential_options(post, options)
|
|
82
83
|
add_transaction_data(post, options)
|
|
83
84
|
add_3ds(post, options)
|
|
84
85
|
end
|
|
@@ -138,6 +139,26 @@ module ActiveMerchant #:nodoc:
|
|
|
138
139
|
post[:previous_payment_id] = options[:previous_charge_id] if options[:previous_charge_id]
|
|
139
140
|
end
|
|
140
141
|
|
|
142
|
+
def add_stored_credential_options(post, options = {})
|
|
143
|
+
return unless options[:stored_credential]
|
|
144
|
+
|
|
145
|
+
case options[:stored_credential][:initial_transaction]
|
|
146
|
+
when true
|
|
147
|
+
post[:merchant_initiated] = false
|
|
148
|
+
when false
|
|
149
|
+
post[:'source.stored'] = true
|
|
150
|
+
post[:previous_payment_id] = options[:stored_credential][:network_transaction_id] if options[:stored_credential][:network_transaction_id]
|
|
151
|
+
post[:merchant_initiated] = true
|
|
152
|
+
end
|
|
153
|
+
|
|
154
|
+
case options[:stored_credential][:reason_type]
|
|
155
|
+
when 'recurring' || 'installment'
|
|
156
|
+
post[:payment_type] = 'Recurring'
|
|
157
|
+
when 'unscheduled'
|
|
158
|
+
return
|
|
159
|
+
end
|
|
160
|
+
end
|
|
161
|
+
|
|
141
162
|
def add_3ds(post, options)
|
|
142
163
|
if options[:three_d_secure] || options[:execute_threed]
|
|
143
164
|
post[:'3ds'] = {}
|