activemerchant 1.76.0 → 1.77.0

Sign up to get free protection for your applications and to get access to all the features.
Files changed (30) hide show
  1. checksums.yaml +4 -4
  2. data/CHANGELOG +34 -0
  3. data/lib/active_merchant/billing/credit_card.rb +12 -13
  4. data/lib/active_merchant/billing/gateways/authorize_net.rb +7 -0
  5. data/lib/active_merchant/billing/gateways/barclaycard_smartpay.rb +8 -0
  6. data/lib/active_merchant/billing/gateways/borgun.rb +1 -1
  7. data/lib/active_merchant/billing/gateways/card_connect.rb +286 -0
  8. data/lib/active_merchant/billing/gateways/cashnet.rb +14 -2
  9. data/lib/active_merchant/billing/gateways/data_cash.rb +10 -0
  10. data/lib/active_merchant/billing/gateways/elavon.rb +11 -0
  11. data/lib/active_merchant/billing/gateways/element.rb +1 -1
  12. data/lib/active_merchant/billing/gateways/fat_zebra.rb +2 -2
  13. data/lib/active_merchant/billing/gateways/firstdata_e4.rb +2 -0
  14. data/lib/active_merchant/billing/gateways/global_collect.rb +15 -0
  15. data/lib/active_merchant/billing/gateways/global_transport.rb +11 -0
  16. data/lib/active_merchant/billing/gateways/hps.rb +12 -1
  17. data/lib/active_merchant/billing/gateways/litle.rb +1 -1
  18. data/lib/active_merchant/billing/gateways/mercury.rb +14 -1
  19. data/lib/active_merchant/billing/gateways/moneris_us.rb +11 -0
  20. data/lib/active_merchant/billing/gateways/ogone.rb +1 -0
  21. data/lib/active_merchant/billing/gateways/payeezy.rb +9 -2
  22. data/lib/active_merchant/billing/gateways/payflow.rb +8 -1
  23. data/lib/active_merchant/billing/gateways/payment_express.rb +2 -1
  24. data/lib/active_merchant/billing/gateways/redsys.rb +1 -1
  25. data/lib/active_merchant/billing/gateways/safe_charge.rb +2 -2
  26. data/lib/active_merchant/billing/gateways/stripe.rb +33 -15
  27. data/lib/active_merchant/billing/network_tokenization_credit_card.rb +1 -1
  28. data/lib/active_merchant/version.rb +1 -1
  29. data/lib/certs/cacert.pem +60 -0
  30. metadata +4 -3
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA1:
3
- metadata.gz: fe5e2a6f611e503ee6acfb6453f46b914f9b93c4
4
- data.tar.gz: ecdf4eaa3a3d3697aa769239ac59ac4121f5d46a
3
+ metadata.gz: e2916b6ecc76df1529d668ccc2d077d93fbdb68d
4
+ data.tar.gz: 6b87fb1550cd04e17d5091a9b2229c35142efd3f
5
5
  SHA512:
6
- metadata.gz: 506d1d259018973cc2d4c9b6c37442f7fdc8903595a5cd6056ab32fa2608bef32d0e94d1f09179f2b660b99e1197c85c146f0afb0a60cd07a42432ebff0d5fc8
7
- data.tar.gz: 8e8ca9a39966245232a7b64a685939e7852eab12f28fc3f1dc540b9e10a39c04517fd912bc609d56101e4e16d0165fe5b7a1f45570b009a35aaf27be09760284
6
+ metadata.gz: 6a9f27cdd93c846986a4983379f86c7be7a263af8bcd3c240777497e70bda59a0cb4f0aa053edfbbc22f4f4e25d750e5f58a5b7c027fdd93b66b5bbb293466cd
7
+ data.tar.gz: 85016ac5ec4a5d450cb1ac171ed9557dad231711674f3bcd771a26d4de5ae9c11f2b300899249a5dab5c61255b726072878b3beb19838a0898645bbe974dc8d1
data/CHANGELOG CHANGED
@@ -2,6 +2,40 @@
2
2
 
3
3
  == HEAD
4
4
 
5
+ == Version 1.77.0 (January 31, 2018)
6
+ * Authorize.net: Allow Transaction Id to be passed for refuds [nfarve] #2698
7
+ * Forte: ensure unit tests are local-only [bpollack] #2696
8
+ * Moneris US: ensure unit tests are local-only [bpollack] #2696
9
+ * Payflow: Change Verify Method for Amex Cards [nfarve] #2693
10
+ * Safe Charge: fix an issue with variable shadowing in the adapter [bpollack] #2697
11
+ * Crashnet: add scrubbing support [bpollack] #2695
12
+ * Barclays EPDQ: add scrubbing support [bpollack] #2695
13
+ * Fat Zebra: add remote scrubbing test [bpollack] #2695
14
+ * Clearhaus: add remote scrubbing test [bpollack] #2695
15
+ * Borgun: add remote scrubbing test [bpollack] #2695
16
+ * Stripe: Added support for the quickchip entry mode option [rbalsdon]
17
+ * Ogone: Add tests for scrubbing [bpollack] #2700
18
+ * Global Transport: Add scrubbing support [bpollack] #2700
19
+ * HPS: Add scrubbing support [bpollack] #2700
20
+ * FirstData E4: Improve scrubbing and add remote scrubbing test [bpollack] #2700
21
+ * Elavon: Add scrubbing support [bpollack] #2700
22
+ * Data Cash: Add scrubbing support [bpollack] #2700
23
+ * Litle: Fix testing URL [wsmoak] #2673
24
+ * Barclays ePDQ Extra Plus: Add missing Entrust root certificates [pacso] #2614
25
+ * Moneris US: Add scrubbing support [bpollack] #2702
26
+ * Mercury: Add scrubbing support [bpollack] #2702
27
+ * Fat Zebra: Tweak remote scrubbing test [bpollack] #2704
28
+ * Card Connect: Add new gateway [nfarve] #2706
29
+ * Payeezy: Ensure store calls are properly scrubbed [dtykocki] #2709
30
+ * Payeezy: Add unit test for scrubbing store call [dtykocki] #2710
31
+ * Element: Correct URL used by store transactions [dtykocki] #2711
32
+ * Borgun: Add support for specifying TerminalID [bpollack] #2712
33
+ * Barclaycard Smartpay: 3DS Implementation [nfarve] #2714
34
+ * Payeezy: Surface gateway_message on failure [curiousepic] #2717
35
+ * Payment Express: Scrub merchant password [curiousepic] #2723
36
+ * Stripe: Fix Partial Application Fee Refunds [curiousepic] #2713
37
+ * GooglePay: Support network tokenized cards [joshnuss] #2725
38
+
5
39
  == Version 1.76.0 (January 3, 2018)
6
40
  * PayU Latam: Change default text for description [nfarve] #2669
7
41
  * Checkout V2: Allows AVS and CVV result details to come through on authorizations [deedeelavinder] #2650
@@ -176,21 +176,20 @@ module ActiveMerchant #:nodoc:
176
176
  # @return [String]
177
177
  attr_accessor :icc_data
178
178
 
179
- # Returns or sets a fallback reason for a EMV transaction whereby the customer's card entered a fallback scenario.
180
- # This can be an arbitrary string.
179
+ # Returns or sets information about the source of the card data.
181
180
  #
182
181
  # @return [String]
183
- attr_accessor :fallback_reason
184
-
185
- # Returns or sets whether card-present EMV data has been read contactlessly.
186
- #
187
- # @return [true, false]
188
- attr_accessor :contactless_emv
189
-
190
- # Returns or sets whether card-present magstripe data has been read contactlessly.
191
- #
192
- # @return [true, false]
193
- attr_accessor :contactless_magstripe
182
+ attr_accessor :read_method
183
+
184
+ READ_METHOD_DESCRIPTIONS = {
185
+ nil => 'A card reader was not used.',
186
+ 'fallback_no_chip' => 'Magstripe was read because the card has no chip.',
187
+ 'fallback_chip_error' => "Magstripe was read because the card's chip failed.",
188
+ 'contactless' => 'Data was read by a Contactless EMV kernel. Issuer script results are not available.',
189
+ 'contactless_magstripe' => 'Contactless data was read with a non-EMV protocol.',
190
+ 'contact' => 'Data was read using the EMV protocol. Issuer script results may follow.',
191
+ 'contact_quickchip' => 'Data was read by the Quickchip EMV kernel. Issuer script results are not available.',
192
+ }
194
193
 
195
194
  # Returns the ciphertext of the card's encrypted PIN.
196
195
  #
@@ -168,6 +168,7 @@ module ActiveMerchant
168
168
  xml.amount(amount(amount))
169
169
 
170
170
  add_payment_source(xml, payment)
171
+ xml.refTransId(transaction_id_from(options[:transaction_id])) if options[:transaction_id]
171
172
  add_invoice(xml, 'refundTransaction', options)
172
173
  add_customer_data(xml, payment, options)
173
174
  add_settings(xml, payment, options)
@@ -423,6 +424,12 @@ module ActiveMerchant
423
424
  xml.settingValue(options[:header_email_receipt])
424
425
  end
425
426
  end
427
+ if options[:test_request]
428
+ xml.setting do
429
+ xml.settingName("testRequest")
430
+ xml.settingValue("1")
431
+ end
432
+ end
426
433
  end
427
434
  end
428
435
 
@@ -35,6 +35,7 @@ module ActiveMerchant #:nodoc:
35
35
  post[:card] = credit_card_hash(creditcard)
36
36
  post[:billingAddress] = billing_address_hash(options) if options[:billing_address]
37
37
  post[:deliveryAddress] = shipping_address_hash(options) if options[:shipping_address]
38
+ add_3ds(post, options) if options[:execute_threed]
38
39
  commit('authorise', post)
39
40
  end
40
41
 
@@ -222,6 +223,8 @@ module ActiveMerchant #:nodoc:
222
223
  case action
223
224
  when 'store'
224
225
  "#{test? ? self.test_url : self.live_url}/Recurring/v12/storeToken"
226
+ when 'finalize3ds'
227
+ "#{test? ? self.test_url : self.live_url}/Payment/v12/authorise3d"
225
228
  else
226
229
  "#{test? ? self.test_url : self.live_url}/Payment/v12/#{action}"
227
230
  end
@@ -312,6 +315,11 @@ module ActiveMerchant #:nodoc:
312
315
  hash[:shopperReference] = options[:customer] if options[:customer]
313
316
  hash.keep_if { |_, v| v }
314
317
  end
318
+
319
+ def add_3ds(post, options)
320
+ post[:additionalData] = { executeThreeD: 'true' }
321
+ post[:browserInfo] = { userAgent: options[:user_agent], acceptHeader: options[:accept_header] }
322
+ end
315
323
  end
316
324
  end
317
325
  end
@@ -84,6 +84,7 @@ module ActiveMerchant #:nodoc:
84
84
  def add_invoice(post, money, options)
85
85
  post[:TrAmount] = amount(money)
86
86
  post[:TrCurrency] = CURRENCY_CODES[options[:currency] || currency(money)]
87
+ post[:TerminalID] = options[:terminal_id] || '1'
87
88
  end
88
89
 
89
90
  def add_payment_method(post, payment_method)
@@ -129,7 +130,6 @@ module ActiveMerchant #:nodoc:
129
130
  post[:Version] = '1000'
130
131
  post[:Processor] = @options[:processor]
131
132
  post[:MerchantID] = @options[:merchant_id]
132
- post[:TerminalID] = 1
133
133
 
134
134
  url = (test? ? test_url : live_url)
135
135
  request = build_request(action, post)
@@ -0,0 +1,286 @@
1
+ module ActiveMerchant #:nodoc:
2
+ module Billing #:nodoc:
3
+ class CardConnectGateway < Gateway
4
+ self.test_url = 'https://fts.cardconnect.com:6443/cardconnect/rest/'
5
+ self.live_url = 'https://fts.cardconnect.com:8443/cardconnect/rest/'
6
+
7
+ self.supported_countries = ['US']
8
+ self.default_currency = 'USD'
9
+ self.supported_cardtypes = [:visa, :master, :american_express, :discover]
10
+
11
+ self.homepage_url = 'https://cardconnect.com/'
12
+ self.display_name = 'Card Connect'
13
+
14
+ STANDARD_ERROR_CODE_MAPPING = {
15
+ '11' => STANDARD_ERROR_CODE[:card_declined],
16
+ '12' => STANDARD_ERROR_CODE[:incorrect_number],
17
+ '13' => STANDARD_ERROR_CODE[:incorrect_cvc],
18
+ '14' => STANDARD_ERROR_CODE[:incorrect_cvc],
19
+ '15' => STANDARD_ERROR_CODE[:invalid_expiry_date],
20
+ '16' => STANDARD_ERROR_CODE[:expired_card],
21
+ '17' => STANDARD_ERROR_CODE[:incorrect_zip],
22
+ '21' => STANDARD_ERROR_CODE[:config_error],
23
+ '22' => STANDARD_ERROR_CODE[:config_error],
24
+ '23' => STANDARD_ERROR_CODE[:config_error],
25
+ '24' => STANDARD_ERROR_CODE[:processing_error],
26
+ '25' => STANDARD_ERROR_CODE[:processing_error],
27
+ '27' => STANDARD_ERROR_CODE[:processing_error],
28
+ '28' => STANDARD_ERROR_CODE[:processing_error],
29
+ '29' => STANDARD_ERROR_CODE[:processing_error],
30
+ '31' => STANDARD_ERROR_CODE[:processing_error],
31
+ '32' => STANDARD_ERROR_CODE[:processing_error],
32
+ '33' => STANDARD_ERROR_CODE[:card_declined],
33
+ '34' => STANDARD_ERROR_CODE[:card_declined],
34
+ '35' => STANDARD_ERROR_CODE[:incorrect_zip],
35
+ '36' => STANDARD_ERROR_CODE[:processing_error],
36
+ '37' => STANDARD_ERROR_CODE[:incorrect_cvc],
37
+ '41' => STANDARD_ERROR_CODE[:processing_error],
38
+ '42' => STANDARD_ERROR_CODE[:processing_error],
39
+ '43' => STANDARD_ERROR_CODE[:processing_error],
40
+ '44' => STANDARD_ERROR_CODE[:config_error],
41
+ '61' => STANDARD_ERROR_CODE[:processing_error],
42
+ '62' => STANDARD_ERROR_CODE[:processing_error],
43
+ '63' => STANDARD_ERROR_CODE[:processing_error],
44
+ '64' => STANDARD_ERROR_CODE[:config_error],
45
+ '65' => STANDARD_ERROR_CODE[:processing_error],
46
+ '66' => STANDARD_ERROR_CODE[:processing_error],
47
+ '91' => STANDARD_ERROR_CODE[:processing_error],
48
+ '92' => STANDARD_ERROR_CODE[:processing_error],
49
+ '93' => STANDARD_ERROR_CODE[:processing_error],
50
+ '94' => STANDARD_ERROR_CODE[:processing_error],
51
+ '95' => STANDARD_ERROR_CODE[:config_error],
52
+ '96' => STANDARD_ERROR_CODE[:processing_error],
53
+ 'NU' => STANDARD_ERROR_CODE[:card_declined],
54
+ 'N3' => STANDARD_ERROR_CODE[:card_declined],
55
+ 'NJ' => STANDARD_ERROR_CODE[:card_declined],
56
+ '51' => STANDARD_ERROR_CODE[:card_declined],
57
+ 'C2' => STANDARD_ERROR_CODE[:incorrect_cvc],
58
+ '54' => STANDARD_ERROR_CODE[:expired_card],
59
+ '05' => STANDARD_ERROR_CODE[:card_declined],
60
+ '03' => STANDARD_ERROR_CODE[:config_error],
61
+ '60' => STANDARD_ERROR_CODE[:pickup_card]
62
+ }
63
+
64
+ def initialize(options = {})
65
+ requires!(options, :merchant_id, :username, :password)
66
+ require_valid_domain!(options, :domain)
67
+ super
68
+ end
69
+
70
+ def require_valid_domain!(options, param)
71
+ if options.key?(param)
72
+ raise ArgumentError.new('not a valid cardconnect domain') unless /\Dcardconnect.com:\d{1,}\D/ =~ options[param]
73
+ end
74
+ end
75
+
76
+ def purchase(money, payment, options = {})
77
+ if options[:po_number]
78
+ MultiResponse.run do |r|
79
+ r.process { authorize(money, payment, options) }
80
+ r.process { capture(money, r.authorization, options) }
81
+ end
82
+ else
83
+ post = {}
84
+ add_invoice(post, options)
85
+ add_money(post, money)
86
+ add_payment(post, payment)
87
+ add_currency(post, money, options)
88
+ add_address(post, options)
89
+ add_customer_data(post, options)
90
+ add_3DS(post, options)
91
+ post[:capture] = 'Y'
92
+ commit('auth', post)
93
+ end
94
+ end
95
+
96
+ def authorize(money, payment, options = {})
97
+ post = {}
98
+ add_money(post, money)
99
+ add_currency(post, money, options)
100
+ add_invoice(post, options)
101
+ add_payment(post, payment)
102
+ add_address(post, options)
103
+ add_customer_data(post, options)
104
+ add_3DS(post, options)
105
+ commit('auth', post)
106
+ end
107
+
108
+ def capture(money, authorization, options = {})
109
+ post = {}
110
+ add_money(post, money)
111
+ add_reference(post, authorization)
112
+ add_additional_data(post, options)
113
+ commit('capture', post)
114
+ end
115
+
116
+ def refund(money, authorization, options = {})
117
+ post = {}
118
+ add_money(post, money)
119
+ add_reference(post, authorization)
120
+ commit('refund', post)
121
+ end
122
+
123
+ def void(authorization, options = {})
124
+ post = {}
125
+ add_reference(post, authorization)
126
+ commit('void', post)
127
+ end
128
+
129
+ def verify(credit_card, options = {})
130
+ authorize(0, credit_card, options)
131
+ end
132
+
133
+ def supports_scrubbing?
134
+ true
135
+ end
136
+
137
+ def scrub(transcript)
138
+ transcript
139
+ .gsub(%r((Authorization: Basic )\w+), '\1[FILTERED]')
140
+ .gsub(%r(("cvv2\\":\\")\d*), '\1[FILTERED]')
141
+ .gsub(%r(("merchid\\":\\")\d*), '\1[FILTERED]')
142
+ .gsub(%r((&?"account\\":\\")\d*), '\1[FILTERED]')
143
+ .gsub(%r((&?"token\\":\\")\d*), '\1[FILTERED]')
144
+ end
145
+
146
+ private
147
+
148
+ def add_customer_data(post, options)
149
+ post[:email] = options[:email] if options[:email]
150
+ end
151
+
152
+ def add_address(post, options)
153
+ if address = options[:billing_address] || options[:address]
154
+ post[:address] = address[:address1] if address[:address1]
155
+ post[:address].concat(" #{address[:address2]}") if address[:address2]
156
+ post[:city] = address[:city] if address[:city]
157
+ post[:region] = address[:state] if address[:state]
158
+ post[:country] = address[:country] if address[:country]
159
+ post[:postal] = address[:zip] if address[:zip]
160
+ post[:phone] = address[:phone] if address[:phone]
161
+ end
162
+ end
163
+
164
+ def add_money(post, money)
165
+ post[:amount] = amount(money)
166
+ end
167
+
168
+ def add_currency(post, money, options)
169
+ post[:currency] = (options[:currency] || currency(money))
170
+ end
171
+
172
+ def add_invoice(post, options)
173
+ post[:orderid] = options[:order_id]
174
+ post[:ecomind] = (options[:recurring] ? 'R' : 'E')
175
+ end
176
+
177
+ def add_payment(post, payment)
178
+ post[:name] = payment.name
179
+ if card_brand(payment) == 'check'
180
+ add_echeck(post, payment)
181
+ else
182
+ post[:account] = payment.number
183
+ post[:expiry] = expdate(payment)
184
+ post[:cvv2] = payment.verification_value
185
+ end
186
+ end
187
+
188
+ def add_echeck(post, payment)
189
+ post[:accttype] = 'ECHK'
190
+ post[:account] = payment.account_number
191
+ post[:bankaba] = payment.routing_number
192
+ end
193
+
194
+ def add_reference(post, authorization)
195
+ post[:retref] = authorization
196
+ end
197
+
198
+ def add_additional_data(post, options)
199
+ post[:ponumber] = options[:po_number]
200
+ post[:taxamnt] = options[:tax_amount] if options[:tax_amount]
201
+ post[:frtamnt] = options[:freight_amount] if options[:freight_amount]
202
+ post[:dutyamnt] = options[:duty_amount] if options[:duty_amount]
203
+ post[:orderdate] = options[:order_date] if options[:order_date]
204
+ post[:shipfromzip] = options[:ship_from_zip] if options[:ship_from_zip]
205
+ if (shipping_address = options[:shipping_address])
206
+ post[:shiptozip] = shipping_address[:zip]
207
+ post[:shiptocountry] = shipping_address[:country]
208
+ end
209
+ if options[:items]
210
+ post[:items] = options[:items].map do |item|
211
+ updated = {}
212
+ item.each_pair do |k, v|
213
+ updated.merge!(k.to_s.gsub(/_/, '') => v)
214
+ end
215
+ end
216
+ end
217
+ end
218
+
219
+ def add_3DS(post, options)
220
+ post[:secureflag] = options[:secure_flag] if options[:secure_flag]
221
+ post[:securevalue] = options[:secure_value] if options[:secure_value]
222
+ post[:securexid] = options[:secure_xid] if options[:secure_xid]
223
+ end
224
+
225
+ def headers
226
+ {
227
+ 'Authorization' => 'Basic ' + Base64.strict_encode64("#{@options[:username]}:#{@options[:password]}"),
228
+ 'Content-Type' => 'application/json'
229
+ }
230
+ end
231
+
232
+ def expdate(credit_card)
233
+ "#{format(credit_card.month, :two_digits)}#{format(credit_card.year, :two_digits)}"
234
+ end
235
+
236
+ def parse(body)
237
+ JSON.parse(body)
238
+ end
239
+
240
+ def url(action)
241
+ if test?
242
+ test_url + action
243
+ else
244
+ (@options[:domain] ? @options[:domain] : live_url) + action
245
+ end
246
+ end
247
+
248
+ def commit(action, parameters)
249
+ parameters[:merchid] = @options[:merchant_id]
250
+ url = url(action)
251
+ response = parse(ssl_request(:put, url, post_data(parameters), headers))
252
+
253
+ Response.new(
254
+ success_from(response),
255
+ message_from(response),
256
+ response,
257
+ authorization: authorization_from(response),
258
+ avs_result: AVSResult.new(code: response['avsresp']),
259
+ cvv_result: CVVResult.new(response['cvvresp']),
260
+ test: test?,
261
+ error_code: error_code_from(response)
262
+ )
263
+ end
264
+
265
+ def success_from(response)
266
+ response['respstat'] == 'A'
267
+ end
268
+
269
+ def message_from(response)
270
+ response['setlstat'] ? "#{response['resptext']} #{response['setlstat']}" : response['resptext']
271
+ end
272
+
273
+ def authorization_from(response)
274
+ response['retref']
275
+ end
276
+
277
+ def post_data(parameters = {})
278
+ parameters.to_json
279
+ end
280
+
281
+ def error_code_from(response)
282
+ STANDARD_ERROR_CODE_MAPPING[response['respcode']] unless success_from(response)
283
+ end
284
+ end
285
+ end
286
+ end
@@ -3,7 +3,8 @@ module ActiveMerchant #:nodoc:
3
3
  class CashnetGateway < Gateway
4
4
  include Empty
5
5
 
6
- self.live_url = "https://commerce.cashnet.com/"
6
+ self.live_url = "https://commerce.cashnet.com/"
7
+ self.test_url = "https://train.cashnet.com/"
7
8
 
8
9
  self.supported_countries = ["US"]
9
10
  self.supported_cardtypes = [:visa, :master, :american_express, :discover, :diners_club, :jcb]
@@ -54,11 +55,22 @@ module ActiveMerchant #:nodoc:
54
55
  commit('REFUND', money, post)
55
56
  end
56
57
 
58
+ def supports_scrubbing?
59
+ true
60
+ end
61
+
62
+ def scrub(transcript)
63
+ transcript
64
+ .gsub(%r{(password=)[^&]+}, '\1[FILTERED]')
65
+ .gsub(%r{(cardno=)[^&]+}, '\1[FILTERED]')
66
+ .gsub(%r{(cid=)[^&]+}, '\1[FILTERED]')
67
+ end
68
+
57
69
  private
58
70
 
59
71
  def commit(action, money, fields)
60
72
  fields[:amount] = amount(money)
61
- url = live_url + CGI.escape(@options[:merchant_gateway_name])
73
+ url = (test? ? test_url : live_url) + CGI.escape(@options[:merchant_gateway_name])
62
74
  raw_response = ssl_post(url, post_data(action, fields))
63
75
  parsed_response = parse(raw_response)
64
76
 
@@ -77,6 +77,16 @@ module ActiveMerchant
77
77
  commit(build_transaction_refund_request(money, reference))
78
78
  end
79
79
 
80
+ def supports_scrubbing?
81
+ true
82
+ end
83
+
84
+ def scrub(transcript)
85
+ transcript.
86
+ gsub(/(<pan>)\d+(<\/pan>)/i, '\1[FILTERED]\2').
87
+ gsub(/(<cv2>)\d+(<\/cv2>)/i, '\1[FILTERED]\2').
88
+ gsub(/(<password>).+(<\/password>)/i, '\1[FILTERED]\2')
89
+ end
80
90
 
81
91
  private
82
92
 
@@ -136,6 +136,17 @@ module ActiveMerchant #:nodoc:
136
136
  commit(:update, nil, form, options)
137
137
  end
138
138
 
139
+ def supports_scrubbing?
140
+ true
141
+ end
142
+
143
+ def scrub(transcript)
144
+ transcript.
145
+ gsub(%r((&?ssl_pin=)[^&]*)i, '\1[FILTERED]').
146
+ gsub(%r((&?ssl_card_number=)[^&\\n\r\n]*)i, '\1[FILTERED]').
147
+ gsub(%r((&?ssl_cvv2cvc2=)[^&]*)i, '\1[FILTERED]')
148
+ end
149
+
139
150
  private
140
151
 
141
152
  def add_invoice(form,options)
@@ -15,7 +15,7 @@ module ActiveMerchant #:nodoc:
15
15
  self.display_name = 'Element'
16
16
 
17
17
  SERVICE_TEST_URL = 'https://certservices.elementexpress.com/express.asmx'
18
- SERVICE_LIVE_URL = 'https://service.elementexpress.com/express.asmx'
18
+ SERVICE_LIVE_URL = 'https://services.elementexpress.com/express.asmx'
19
19
 
20
20
  def initialize(options={})
21
21
  requires!(options, :account_id, :account_token, :application_id, :acceptor_id, :application_name, :application_version)
@@ -78,8 +78,8 @@ module ActiveMerchant #:nodoc:
78
78
  def scrub(transcript)
79
79
  transcript.
80
80
  gsub(%r((Authorization: Basic )\w+), '\1[FILTERED]').
81
- gsub(%r(("card_number\\":\\")[^"\\]*)i, '\1[FILTERED]').
82
- gsub(%r(("cvv\\":\\")\d+), '\1[FILTERED]')
81
+ gsub(%r(("card_number\\?":\\?")[^"\\]*)i, '\1[FILTERED]').
82
+ gsub(%r(("cvv\\?":\\?")\d+), '\1[FILTERED]')
83
83
  end
84
84
 
85
85
  private
@@ -144,7 +144,9 @@ module ActiveMerchant #:nodoc:
144
144
  transcript
145
145
  .gsub(%r((<Card_Number>).+(</Card_Number>)), '\1[FILTERED]\2')
146
146
  .gsub(%r((<VerificationStr2>).+(</VerificationStr2>)), '\1[FILTERED]\2')
147
+ .gsub(%r((<Password>).+(</Password>))i, '\1[FILTERED]\2')
147
148
  .gsub(%r((<CAVV>).+(</CAVV>)), '\1[FILTERED]\2')
149
+ .gsub(%r((Card Number : ).*\d)i, '\1[FILTERED]')
148
150
  end
149
151
 
150
152
  def supports_network_tokenization?
@@ -33,6 +33,7 @@ module ActiveMerchant #:nodoc:
33
33
  add_payment(post, payment, options)
34
34
  add_customer_data(post, options, payment)
35
35
  add_address(post, payment, options)
36
+ add_creator_info(post, options)
36
37
 
37
38
  commit(:authorize, post)
38
39
  end
@@ -41,6 +42,7 @@ module ActiveMerchant #:nodoc:
41
42
  post = nestable_hash
42
43
  add_order(post, money, options)
43
44
  add_customer_data(post, options)
45
+ add_creator_info(post, options)
44
46
  commit(:capture, post, authorization)
45
47
  end
46
48
 
@@ -48,11 +50,13 @@ module ActiveMerchant #:nodoc:
48
50
  post = nestable_hash
49
51
  add_amount(post, money, options)
50
52
  add_refund_customer_data(post, options)
53
+ add_creator_info(post, options)
51
54
  commit(:refund, post, authorization)
52
55
  end
53
56
 
54
57
  def void(authorization, options={})
55
58
  post = nestable_hash
59
+ add_creator_info(post, options)
56
60
  commit(:void, post, authorization)
57
61
  end
58
62
 
@@ -99,6 +103,17 @@ module ActiveMerchant #:nodoc:
99
103
  }
100
104
  end
101
105
 
106
+ def add_creator_info(post, options)
107
+ post['sdkIdentifier'] = options[:sdk_identifier] if options[:sdk_identifier]
108
+ post['sdkCreator'] = options[:sdk_creator] if options[:sdk_creator]
109
+ post['integrator'] = options[:integrator] if options[:integrator]
110
+ post['shoppingCartExtension'] = {}
111
+ post['shoppingCartExtension']['creator'] = options[:creator] if options[:creator]
112
+ post['shoppingCartExtension']['name'] = options[:name] if options[:name]
113
+ post['shoppingCartExtension']['version'] = options[:version] if options[:version]
114
+ post['shoppingCartExtension']['extensionID'] = options[:extension_ID] if options[:extension_ID]
115
+ end
116
+
102
117
  def add_amount(post, money, options={})
103
118
  post["amountOfMoney"] = {
104
119
  "amount" => amount(money),
@@ -75,6 +75,17 @@ module ActiveMerchant #:nodoc:
75
75
  commit('CardVerify', post, options)
76
76
  end
77
77
 
78
+ def supports_scrubbing?
79
+ true
80
+ end
81
+
82
+ def scrub(transcript)
83
+ transcript.
84
+ gsub(%r((&?CardNum=)[^&]*)i, '\1[FILTERED]').
85
+ gsub(%r((&?CVNum=)[^&]*)i, '\1[FILTERED]').
86
+ gsub(%r((&?GlobalPassword=)[^&]*)i, '\1[FILTERED]')
87
+ end
88
+
78
89
  private
79
90
 
80
91
  def add_address(post, options)
@@ -73,6 +73,17 @@ module ActiveMerchant #:nodoc:
73
73
  end
74
74
  end
75
75
 
76
+ def supports_scrubbing?
77
+ true
78
+ end
79
+
80
+ def scrub(transcript)
81
+ transcript.
82
+ gsub(%r((<hps:CardNbr>)[^<]*(<\/hps:CardNbr>))i, '\1[FILTERED]\2').
83
+ gsub(%r((<hps:CVV2>)[^<]*(<\/hps:CVV2>))i, '\1[FILTERED]\2').
84
+ gsub(%r((<hps:SecretAPIKey>)[^<]*(<\/hps:SecretAPIKey>))i, '\1[FILTERED]\2')
85
+ end
86
+
76
87
  private
77
88
 
78
89
  def add_reference(xml, transaction_id)
@@ -218,7 +229,7 @@ module ActiveMerchant #:nodoc:
218
229
  data = build_request(action, &request)
219
230
 
220
231
  response = begin
221
- parse(ssl_post((test? ? test_url : live_url), data, 'Content-type' => 'text/xml'))
232
+ parse(ssl_post((test? ? test_url : live_url), data, 'Content-Type' => 'text/xml'))
222
233
  rescue ResponseError => e
223
234
  parse(e.response.body)
224
235
  end
@@ -5,7 +5,7 @@ module ActiveMerchant #:nodoc:
5
5
  class LitleGateway < Gateway
6
6
  SCHEMA_VERSION = '9.12'
7
7
 
8
- self.test_url = 'https://www.testlitle.com/sandbox/communicator/online'
8
+ self.test_url = 'https://www.testvantivcnp.com/sandbox/communicator/online'
9
9
  self.live_url = 'https://payments.vantivcnp.com/vap/communicator/online'
10
10
 
11
11
  self.supported_countries = ['US']
@@ -81,6 +81,19 @@ module ActiveMerchant #:nodoc:
81
81
  commit('CardLookup', request)
82
82
  end
83
83
 
84
+ def supports_scrubbing?
85
+ true
86
+ end
87
+
88
+ def scrub(transcript)
89
+ transcript.
90
+ gsub(%r(&lt;), "<").
91
+ gsub(%r(&gt;), ">").
92
+ gsub(%r((<pw>).*(</pw>))i, '\1[FILTERED]\2').
93
+ gsub(%r((<AcctNo>)(\d|x)*(</AcctNo>))i, '\1[FILTERED]\3').
94
+ gsub(%r((<CVVData>)\d*(</CVVData>))i, '\1[FILTERED]\2')
95
+ end
96
+
84
97
  private
85
98
 
86
99
  def build_non_authorized_request(action, money, credit_card, options)
@@ -126,7 +139,7 @@ module ActiveMerchant #:nodoc:
126
139
  xml.tag! 'TranInfo' do
127
140
  xml.tag! "AuthCode", auth_code
128
141
  xml.tag! "AcqRefData", acq_ref_data
129
- xml.tag! "ProcessData", process_data
142
+ xml.tag! "ProcessData", process_data
130
143
  end
131
144
  end
132
145
  end
@@ -137,6 +137,17 @@ module ActiveMerchant #:nodoc:
137
137
  commit('us_res_update_cc', post)
138
138
  end
139
139
 
140
+ def supports_scrubbing?
141
+ true
142
+ end
143
+
144
+ def scrub(transcript)
145
+ transcript.
146
+ gsub(%r((<pan>)[^<]*(</pan>))i, '\1[FILTERED]\2').
147
+ gsub(%r((<api_token>)[^<]*(</api_token>))i, '\1[FILTERED]\2').
148
+ gsub(%r((<cvd_value>)[^<]*(</cvd_value>))i, '\1[FILTERED]\2')
149
+ end
150
+
140
151
  private # :nodoc: all
141
152
 
142
153
  def expdate(creditcard)
@@ -334,6 +334,7 @@ module ActiveMerchant #:nodoc:
334
334
  def add_invoice(post, options)
335
335
  add_pair post, 'orderID', options[:order_id] || generate_unique_id[0...30]
336
336
  add_pair post, 'COM', options[:description]
337
+ add_pair post, 'ORIG', options[:origin] if options[:origin]
337
338
  end
338
339
 
339
340
  def add_creditcard(post, creditcard)
@@ -104,10 +104,17 @@ module ActiveMerchant
104
104
  def scrub(transcript)
105
105
  transcript.
106
106
  gsub(%r((Token: )(\w|-)+), '\1[FILTERED]').
107
+ gsub(%r((Apikey: )(\w|-)+), '\1[FILTERED]').
107
108
  gsub(%r((\\?"card_number\\?":\\?")\d+), '\1[FILTERED]').
108
109
  gsub(%r((\\?"cvv\\?":\\?")\d+), '\1[FILTERED]').
109
110
  gsub(%r((\\?"account_number\\?":\\?")\d+), '\1[FILTERED]').
110
- gsub(%r((\\?"routing_number\\?":\\?")\d+), '\1[FILTERED]')
111
+ gsub(%r((\\?"routing_number\\?":\\?")\d+), '\1[FILTERED]').
112
+ gsub(%r((\\?card_number=)\d+(&?)), '\1[FILTERED]').
113
+ gsub(%r((\\?cvv=)\d+(&?)), '\1[FILTERED]').
114
+ gsub(%r((\\?apikey=)\w+(&?)), '\1[FILTERED]').
115
+ gsub(%r{(\\?"credit_card\.card_number\\?":)(\\?"[^"]+\\?")}, '\1[FILTERED]').
116
+ gsub(%r{(\\?"credit_card\.cvv\\?":)(\\?"[^"]+\\?")}, '\1[FILTERED]').
117
+ gsub(%r{(\\?"apikey\\?":)(\\?"[^"]+\\?")}, '\1[FILTERED]')
111
118
  end
112
119
 
113
120
  private
@@ -345,7 +352,7 @@ module ActiveMerchant
345
352
  elsif response.key?('fault')
346
353
  response['fault'].to_h['faultstring']
347
354
  else
348
- response['bank_message'] || 'Failure to successfully create token.'
355
+ response['bank_message'] || response['gateway_message'] || 'Failure to successfully create token.'
349
356
  end
350
357
  end
351
358
 
@@ -45,7 +45,14 @@ module ActiveMerchant #:nodoc:
45
45
  end
46
46
 
47
47
  def verify(payment, options={})
48
- authorize(0, payment, options)
48
+ if credit_card_type(payment) == 'Amex'
49
+ MultiResponse.run(:use_first_response) do |r|
50
+ r.process { authorize(100, payment, options) }
51
+ r.process(:ignore_result) { void(r.authorization, options) }
52
+ end
53
+ else
54
+ authorize(0, payment, options)
55
+ end
49
56
  end
50
57
 
51
58
  def verify_credentials
@@ -128,7 +128,8 @@ module ActiveMerchant #:nodoc:
128
128
 
129
129
  def scrub(transcript)
130
130
  transcript.
131
- gsub(%r((Authorization: Basic )\w+), '\1[FILTERED]').
131
+ gsub(%r((<PostPassword>).+(</PostPassword>)), '\1[FILTERED]\2').
132
+ gsub(%r((Authorization: Basic )\w+), '\1[FILTERED]\2').
132
133
  gsub(%r((<CardNumber>)\d+(</CardNumber>)), '\1[FILTERED]\2').
133
134
  gsub(%r((<Cvc2>)\d+(</Cvc2>)), '\1[FILTERED]\2')
134
135
  end
@@ -491,7 +491,7 @@ module ActiveMerchant #:nodoc:
491
491
 
492
492
  def encrypt(key, order_id)
493
493
  block_length = 8
494
- cipher = OpenSSL::Cipher::Cipher.new('DES3')
494
+ cipher = OpenSSL::Cipher.new('DES3')
495
495
  cipher.encrypt
496
496
 
497
497
  cipher.key = Base64.strict_decode64(key)
@@ -170,8 +170,8 @@ module ActiveMerchant #:nodoc:
170
170
  if childnode.elements.size == 0
171
171
  element_name_to_symbol(response, childnode)
172
172
  else
173
- childnode.traverse do |childnode|
174
- element_name_to_symbol(response, childnode)
173
+ childnode.traverse do |node|
174
+ element_name_to_symbol(response, node)
175
175
  end
176
176
  end
177
177
  end
@@ -112,6 +112,7 @@ module ActiveMerchant #:nodoc:
112
112
  end
113
113
  r.process do
114
114
  post = create_post_for_auth_or_purchase(money, payment, options)
115
+ post[:card][:processing_method] = 'quick_chip' if quickchip_payment?(payment)
115
116
  commit(:post, 'charges', post, options)
116
117
  end
117
118
  end.responses.last
@@ -150,7 +151,7 @@ module ActiveMerchant #:nodoc:
150
151
 
151
152
  return r unless options[:refund_fee_amount]
152
153
 
153
- r.process { fetch_application_fees(identification, options) }
154
+ r.process { fetch_application_fee(identification, options) }
154
155
  r.process { refund_application_fee(options[:refund_fee_amount], application_fee_from_response(r.responses.last), options) }
155
156
  end
156
157
  end
@@ -165,9 +166,7 @@ module ActiveMerchant #:nodoc:
165
166
 
166
167
  def application_fee_from_response(response)
167
168
  return unless response.success?
168
-
169
- application_fees = response.params["data"].select { |fee| fee["object"] == "application_fee" }
170
- application_fees.first["id"] unless application_fees.empty?
169
+ response.params["application_fee"] unless response.params["application_fee"].empty?
171
170
  end
172
171
 
173
172
  def refund_application_fee(money, identification, options = {})
@@ -175,9 +174,11 @@ module ActiveMerchant #:nodoc:
175
174
 
176
175
  post = {}
177
176
  add_amount(post, money, options)
178
- options.merge!(:key => @fee_refund_api_key)
177
+ options.merge!(:key => @fee_refund_api_key) if @fee_refund_api_key
178
+ options.delete(:stripe_account)
179
179
 
180
- commit(:post, "application_fees/#{CGI.escape(identification)}/refund", post, options)
180
+ refund_fee = commit(:post, "application_fees/#{CGI.escape(identification)}/refunds", post, options)
181
+ application_fee_response!(refund_fee, "Application fee could not be refunded: #{refund_fee.message}")
181
182
  end
182
183
 
183
184
  # Note: creating a new credit card will not change the customer's existing default credit card (use :set_default => true)
@@ -305,6 +306,7 @@ module ActiveMerchant #:nodoc:
305
306
 
306
307
  if emv_payment?(payment)
307
308
  add_statement_address(post, options)
309
+ add_emv_metadata(post, payment)
308
310
  else
309
311
  add_amount(post, money, options, true)
310
312
  add_customer_data(post, options)
@@ -369,7 +371,7 @@ module ActiveMerchant #:nodoc:
369
371
 
370
372
  def add_statement_address(post, options)
371
373
  return unless statement_address = options[:statement_address]
372
- return unless [:address1, :city, :zip, :state].all? { |key| statement_address[key].present? }
374
+ return unless [:address1, :city, :zip, :state].all? { |key| statement_address[key].present? }
373
375
 
374
376
  post[:statement_address] = {}
375
377
  post[:statement_address][:line1] = statement_address[:address1]
@@ -383,8 +385,7 @@ module ActiveMerchant #:nodoc:
383
385
  card = {}
384
386
  if emv_payment?(creditcard)
385
387
  add_emv_creditcard(post, creditcard.icc_data)
386
- post[:card][:read_method] = "contactless" if creditcard.contactless_emv
387
- post[:card][:read_method] = "contactless_magstripe_mode" if creditcard.contactless_magstripe
388
+ post[:card][:read_method] = "contactless" if creditcard.read_method == 'contactless'
388
389
  if creditcard.encrypted_pin_cryptogram.present? && creditcard.encrypted_pin_ksn.present?
389
390
  post[:card][:encrypted_pin] = creditcard.encrypted_pin_cryptogram
390
391
  post[:card][:encrypted_pin_key_id] = creditcard.encrypted_pin_ksn
@@ -392,9 +393,11 @@ module ActiveMerchant #:nodoc:
392
393
  elsif creditcard.respond_to?(:number)
393
394
  if creditcard.respond_to?(:track_data) && creditcard.track_data.present?
394
395
  card[:swipe_data] = creditcard.track_data
395
- card[:fallback_reason] = creditcard.fallback_reason if creditcard.fallback_reason
396
- card[:read_method] = "contactless" if creditcard.contactless_emv
397
- card[:read_method] = "contactless_magstripe_mode" if creditcard.contactless_magstripe
396
+ if creditcard.respond_to?(:read_method)
397
+ card[:fallback_reason] = 'no_chip' if creditcard.read_method == 'fallback_no_chip'
398
+ card[:fallback_reason] = 'chip_error' if creditcard.read_method == 'fallback_chip_error'
399
+ card[:read_method] = "contactless_magstripe_mode" if creditcard.read_method == 'contactless_magstripe'
400
+ end
398
401
  else
399
402
  card[:number] = creditcard.number
400
403
  card[:exp_month] = creditcard.month
@@ -446,16 +449,27 @@ module ActiveMerchant #:nodoc:
446
449
  end
447
450
 
448
451
  def add_metadata(post, options = {})
449
- post[:metadata] = options[:metadata] || {}
452
+ post[:metadata] ||= {}
453
+ post[:metadata].merge!(options[:metadata]) if options[:metadata]
450
454
  post[:metadata][:email] = options[:email] if options[:email]
451
455
  post[:metadata][:order_id] = options[:order_id] if options[:order_id]
452
456
  post.delete(:metadata) if post[:metadata].empty?
453
457
  end
454
458
 
455
- def fetch_application_fees(identification, options = {})
459
+ def add_emv_metadata(post, creditcard)
460
+ post[:metadata] ||= {}
461
+ post[:metadata][:card_read_method] = creditcard.read_method if creditcard.respond_to?(:read_method)
462
+ end
463
+
464
+ def fetch_application_fee(identification, options = {})
456
465
  options.merge!(:key => @fee_refund_api_key)
457
466
 
458
- commit(:get, "application_fees?charge=#{identification}", nil, options)
467
+ fetch_charge = commit(:get, "charges/#{CGI.escape(identification)}", nil, options)
468
+ application_fee_response!(fetch_charge, "Application fee id could not be retrieved: #{fetch_charge.message}")
469
+ end
470
+
471
+ def application_fee_response!(response, message)
472
+ response.success? ? response : Response.new(false, message)
459
473
  end
460
474
 
461
475
  def parse(body)
@@ -586,6 +600,10 @@ module ActiveMerchant #:nodoc:
586
600
  payment.respond_to?(:emv?) && payment.emv?
587
601
  end
588
602
 
603
+ def quickchip_payment?(payment)
604
+ payment.respond_to?(:read_method) && payment.read_method == 'contact_quickchip'
605
+ end
606
+
589
607
  def card_from_response(response)
590
608
  response["card"] || response["active_card"] || response["source"] || {}
591
609
  end
@@ -17,7 +17,7 @@ module ActiveMerchant #:nodoc:
17
17
  attr_accessor :payment_cryptogram, :eci, :transaction_id
18
18
  attr_writer :source
19
19
 
20
- SOURCES = [:apple_pay, :android_pay]
20
+ SOURCES = %i(apple_pay android_pay google_pay)
21
21
 
22
22
  def source
23
23
  if defined?(@source) && SOURCES.include?(@source)
@@ -1,3 +1,3 @@
1
1
  module ActiveMerchant
2
- VERSION = "1.76.0"
2
+ VERSION = "1.77.0"
3
3
  end
@@ -501,6 +501,66 @@ W3iDVuycNsMm4hH2Z0kdkquM++v/eu6FSqdQgPCnXEqULl8FmTxSQeDNtGPPAUO6nIPcj2A781q0
501
501
  tHuu2guQOHXvgR1m0vdXcDazv/wor3ElhVsT/h5/WrQ8
502
502
  -----END CERTIFICATE-----
503
503
 
504
+ Entrust G2 Root Certificate Authority
505
+ =====================================
506
+ -----BEGIN CERTIFICATE-----
507
+ MIIEPjCCAyagAwIBAgIESlOMKDANBgkqhkiG9w0BAQsFADCBvjELMAkGA1UEBhMC
508
+ VVMxFjAUBgNVBAoTDUVudHJ1c3QsIEluYy4xKDAmBgNVBAsTH1NlZSB3d3cuZW50
509
+ cnVzdC5uZXQvbGVnYWwtdGVybXMxOTA3BgNVBAsTMChjKSAyMDA5IEVudHJ1c3Qs
510
+ IEluYy4gLSBmb3IgYXV0aG9yaXplZCB1c2Ugb25seTEyMDAGA1UEAxMpRW50cnVz
511
+ dCBSb290IENlcnRpZmljYXRpb24gQXV0aG9yaXR5IC0gRzIwHhcNMDkwNzA3MTcy
512
+ NTU0WhcNMzAxMjA3MTc1NTU0WjCBvjELMAkGA1UEBhMCVVMxFjAUBgNVBAoTDUVu
513
+ dHJ1c3QsIEluYy4xKDAmBgNVBAsTH1NlZSB3d3cuZW50cnVzdC5uZXQvbGVnYWwt
514
+ dGVybXMxOTA3BgNVBAsTMChjKSAyMDA5IEVudHJ1c3QsIEluYy4gLSBmb3IgYXV0
515
+ aG9yaXplZCB1c2Ugb25seTEyMDAGA1UEAxMpRW50cnVzdCBSb290IENlcnRpZmlj
516
+ YXRpb24gQXV0aG9yaXR5IC0gRzIwggEiMA0GCSqGSIb3DQEBAQUAA4IBDwAwggEK
517
+ AoIBAQC6hLZy254Ma+KZ6TABp3bqMriVQRrJ2mFOWHLP/vaCeb9zYQYKpSfYs1/T
518
+ RU4cctZOMvJyig/3gxnQaoCAAEUesMfnmr8SVycco2gvCoe9amsOXmXzHHfV1IWN
519
+ cCG0szLni6LVhjkCsbjSR87kyUnEO6fe+1R9V77w6G7CebI6C1XiUJgWMhNcL3hW
520
+ wcKUs/Ja5CeanyTXxuzQmyWC48zCxEXFjJd6BmsqEZ+pCm5IO2/b1BEZQvePB7/1
521
+ U1+cPvQXLOZprE4yTGJ36rfo5bs0vBmLrpxR57d+tVOxMyLlbc9wPBr64ptntoP0
522
+ jaWvYkxN4FisZDQSA/i2jZRjJKRxAgMBAAGjQjBAMA4GA1UdDwEB/wQEAwIBBjAP
523
+ BgNVHRMBAf8EBTADAQH/MB0GA1UdDgQWBBRqciZ60B7vfec7aVHUbI2fkBJmqzAN
524
+ BgkqhkiG9w0BAQsFAAOCAQEAeZ8dlsa2eT8ijYfThwMEYGprmi5ZiXMRrEPR9RP/
525
+ jTkrwPK9T3CMqS/qF8QLVJ7UG5aYMzyorWKiAHarWWluBh1+xLlEjZivEtRh2woZ
526
+ Rkfz6/djwUAFQKXSt/S1mja/qYh2iARVBCuch38aNzx+LaUa2NSJXsq9rD1s2G2v
527
+ 1fN2D807iDginWyTmsQ9v4IbZT+mD12q/OWyFcq1rca8PdCE6OoGcrBNOTJ4vz4R
528
+ nAuknZoh8/CbCzB428Hch0P+vGOaysXCHMnHjf87ElgI5rY97HosTvuDls4MPGmH
529
+ VHOkc8KT/1EQrBVUAdj8BbGJoX90g5pJ19xOe4pIb4tF9g==
530
+ -----END CERTIFICATE-----
531
+
532
+ Entrust L1M Chain Root Certificate
533
+ ==================================
534
+ -----BEGIN CERTIFICATE-----
535
+ MIIE/zCCA+egAwIBAgIEUdNARDANBgkqhkiG9w0BAQsFADCBsDELMAkGA1UEBhMC
536
+ VVMxFjAUBgNVBAoTDUVudHJ1c3QsIEluYy4xOTA3BgNVBAsTMHd3dy5lbnRydXN0
537
+ Lm5ldC9DUFMgaXMgaW5jb3Jwb3JhdGVkIGJ5IHJlZmVyZW5jZTEfMB0GA1UECxMW
538
+ KGMpIDIwMDYgRW50cnVzdCwgSW5jLjEtMCsGA1UEAxMkRW50cnVzdCBSb290IENl
539
+ cnRpZmljYXRpb24gQXV0aG9yaXR5MB4XDTE0MDkyMjE3MTQ1N1oXDTI0MDkyMzAx
540
+ MzE1M1owgb4xCzAJBgNVBAYTAlVTMRYwFAYDVQQKEw1FbnRydXN0LCBJbmMuMSgw
541
+ JgYDVQQLEx9TZWUgd3d3LmVudHJ1c3QubmV0L2xlZ2FsLXRlcm1zMTkwNwYDVQQL
542
+ EzAoYykgMjAwOSBFbnRydXN0LCBJbmMuIC0gZm9yIGF1dGhvcml6ZWQgdXNlIG9u
543
+ bHkxMjAwBgNVBAMTKUVudHJ1c3QgUm9vdCBDZXJ0aWZpY2F0aW9uIEF1dGhvcml0
544
+ eSAtIEcyMIIBIjANBgkqhkiG9w0BAQEFAAOCAQ8AMIIBCgKCAQEAuoS2ctueDGvi
545
+ mekwAad26jK4lUEaydphTlhyz/72gnm/c2EGCqUn2LNf00VOHHLWTjLycooP94MZ
546
+ 0GqAgABFHrDH55q/ElcnHKNoLwqHvWprDl5l8xx31dSFjXAhtLMy54ui1YY5ArG4
547
+ 0kfO5MlJxDun3vtUfVe+8OhuwnmyOgtV4lCYFjITXC94VsHClLPyWuQnmp8k18bs
548
+ 0JslguPMwsRFxYyXegZrKhGfqQpuSDtv29QRGUL3jwe/9VNfnD70FyzmaaxOMkxi
549
+ d+q36OW7NLwZi66cUee3frVTsTMi5W3PcDwa+uKbZ7aD9I2lr2JMTeBYrGQ0EgP4
550
+ to2UYySkcQIDAQABo4IBDzCCAQswDgYDVR0PAQH/BAQDAgEGMBIGA1UdEwEB/wQI
551
+ MAYBAf8CAQEwMwYIKwYBBQUHAQEEJzAlMCMGCCsGAQUFBzABhhdodHRwOi8vb2Nz
552
+ cC5lbnRydXN0Lm5ldDAzBgNVHR8ELDAqMCigJqAkhiJodHRwOi8vY3JsLmVudHJ1
553
+ c3QubmV0L3Jvb3RjYTEuY3JsMDsGA1UdIAQ0MDIwMAYEVR0gADAoMCYGCCsGAQUF
554
+ BwIBFhpodHRwOi8vd3d3LmVudHJ1c3QubmV0L0NQUzAdBgNVHQ4EFgQUanImetAe
555
+ 733nO2lR1GyNn5ASZqswHwYDVR0jBBgwFoAUaJDkZ6SmU4DHhmak8fdLQ/uEvW0w
556
+ DQYJKoZIhvcNAQELBQADggEBAGkzg/woem99751V68U+ep11s8zDODbZNKIoaBjq
557
+ HmnTvefQd9q4AINOSs9v0fHBIj905PeYSZ6btp7h25h3LVY0sag82f3Azce/BQPU
558
+ AsXx5cbaCKUTx2IjEdFhMB1ghEXveajGJpOkt800uGnFE/aRs8lFc3a2kvZ2Clvh
559
+ A0e36SlMkTIjN0qcNdh4/R0f5IOJJICtt/nP5F2l1HHEhVtwH9s/HAHrGkUmMRTM
560
+ Zb9n3srMM2XlQZHXN75BGpad5oqXnafOrE6aPb0BoGrZTyIAi0TVaWJ7LuvMuueS
561
+ fWlnPfy4fN5Bh9Bp6roKGHoalUOzeXEodm2h+1dK7E3IDhA=
562
+ -----END CERTIFICATE-----
563
+
504
564
  RSA Security 2048 v3
505
565
  ====================
506
566
  -----BEGIN CERTIFICATE-----
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: activemerchant
3
3
  version: !ruby/object:Gem::Version
4
- version: 1.76.0
4
+ version: 1.77.0
5
5
  platform: ruby
6
6
  authors:
7
7
  - Tobias Luetke
8
8
  autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
- date: 2018-01-03 00:00:00.000000000 Z
11
+ date: 2018-01-31 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: activesupport
@@ -187,6 +187,7 @@ files:
187
187
  - lib/active_merchant/billing/gateways/braintree_orange.rb
188
188
  - lib/active_merchant/billing/gateways/bridge_pay.rb
189
189
  - lib/active_merchant/billing/gateways/cams.rb
190
+ - lib/active_merchant/billing/gateways/card_connect.rb
190
191
  - lib/active_merchant/billing/gateways/card_save.rb
191
192
  - lib/active_merchant/billing/gateways/card_stream.rb
192
193
  - lib/active_merchant/billing/gateways/cardknox.rb
@@ -415,7 +416,7 @@ required_rubygems_version: !ruby/object:Gem::Requirement
415
416
  version: '0'
416
417
  requirements: []
417
418
  rubyforge_project: activemerchant
418
- rubygems_version: 2.5.2.1
419
+ rubygems_version: 2.6.14
419
420
  signing_key:
420
421
  specification_version: 4
421
422
  summary: Framework and tools for dealing with credit card transactions.