activemerchant 1.52.0 → 1.53.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 +56 -0
- data/README.md +1 -1
- data/lib/active_merchant/billing/gateways/authorize_net.rb +4 -1
- data/lib/active_merchant/billing/gateways/banwire.rb +11 -0
- data/lib/active_merchant/billing/gateways/beanstream.rb +12 -1
- data/lib/active_merchant/billing/gateways/blue_pay.rb +519 -506
- data/lib/active_merchant/billing/gateways/borgun.rb +10 -0
- data/lib/active_merchant/billing/gateways/braintree/braintree_common.rb +13 -1
- data/lib/active_merchant/billing/gateways/braintree_blue.rb +2 -2
- data/lib/active_merchant/billing/gateways/braintree_orange.rb +0 -1
- data/lib/active_merchant/billing/gateways/card_stream.rb +14 -19
- data/lib/active_merchant/billing/gateways/cecabank.rb +11 -1
- data/lib/active_merchant/billing/gateways/cenpos.rb +62 -2
- data/lib/active_merchant/billing/gateways/checkout.rb +1 -1
- data/lib/active_merchant/billing/gateways/checkout_v2.rb +3 -3
- data/lib/active_merchant/billing/gateways/conekta.rb +11 -1
- data/lib/active_merchant/billing/gateways/creditcall.rb +208 -0
- data/lib/active_merchant/billing/gateways/epay.rb +12 -0
- data/lib/active_merchant/billing/gateways/eway.rb +11 -0
- data/lib/active_merchant/billing/gateways/eway_rapid.rb +11 -0
- data/lib/active_merchant/billing/gateways/forte.rb +238 -0
- data/lib/active_merchant/billing/gateways/iridium.rb +11 -0
- data/lib/active_merchant/billing/gateways/jetpay.rb +10 -1
- data/lib/active_merchant/billing/gateways/linkpoint.rb +11 -0
- data/lib/active_merchant/billing/gateways/litle.rb +8 -1
- data/lib/active_merchant/billing/gateways/merchant_ware_version_four.rb +1 -1
- data/lib/active_merchant/billing/gateways/micropayment.rb +167 -0
- data/lib/active_merchant/billing/gateways/migs.rb +13 -4
- data/lib/active_merchant/billing/gateways/monei.rb +1 -1
- data/lib/active_merchant/billing/gateways/netbilling.rb +11 -1
- data/lib/active_merchant/billing/gateways/nmi.rb +164 -178
- data/lib/active_merchant/billing/gateways/ogone.rb +50 -15
- data/lib/active_merchant/billing/gateways/openpay.rb +10 -1
- data/lib/active_merchant/billing/gateways/pac_net_raven.rb +5 -5
- data/lib/active_merchant/billing/gateways/payment_express.rb +11 -0
- data/lib/active_merchant/billing/gateways/paymill.rb +11 -0
- data/lib/active_merchant/billing/gateways/paypal/paypal_common_api.rb +1 -1
- data/lib/active_merchant/billing/gateways/paystation.rb +3 -4
- data/lib/active_merchant/billing/gateways/pin.rb +10 -0
- data/lib/active_merchant/billing/gateways/quickpay/quickpay_v10.rb +106 -57
- data/lib/active_merchant/billing/gateways/realex.rb +10 -0
- data/lib/active_merchant/billing/gateways/redsys.rb +20 -0
- data/lib/active_merchant/billing/gateways/s5.rb +1 -0
- data/lib/active_merchant/billing/gateways/sage_pay.rb +11 -0
- data/lib/active_merchant/billing/gateways/secure_net.rb +1 -0
- data/lib/active_merchant/billing/gateways/stripe.rb +10 -4
- data/lib/active_merchant/billing/gateways/tns.rb +15 -4
- data/lib/active_merchant/billing/gateways/trust_commerce.rb +11 -0
- data/lib/active_merchant/billing/gateways/usa_epay_transaction.rb +12 -2
- data/lib/active_merchant/billing/gateways/wirecard.rb +11 -1
- data/lib/active_merchant/billing/gateways/worldpay.rb +11 -0
- data/lib/active_merchant/billing/gateways/worldpay_online_payments.rb +1 -1
- data/lib/active_merchant/version.rb +1 -1
- metadata +5 -2
@@ -109,6 +109,18 @@ module ActiveMerchant #:nodoc:
|
|
109
109
|
refund(money, identification, options)
|
110
110
|
end
|
111
111
|
|
112
|
+
def supports_scrubbing
|
113
|
+
true
|
114
|
+
end
|
115
|
+
|
116
|
+
def scrub(transcript)
|
117
|
+
transcript.
|
118
|
+
gsub(%r((Authorization: Basic )\w+), '\1[FILTERED]').
|
119
|
+
gsub(%r(((?:\?|&)cardno=)\d*(&?)), '\1[FILTERED]\2').
|
120
|
+
gsub(%r((&?cvc=)\d*(&?)), '\1[FILTERED]\2')
|
121
|
+
end
|
122
|
+
|
123
|
+
|
112
124
|
private
|
113
125
|
|
114
126
|
def add_amount(post, money, options)
|
@@ -52,6 +52,17 @@ module ActiveMerchant #:nodoc:
|
|
52
52
|
commit(refund_url, money, post)
|
53
53
|
end
|
54
54
|
|
55
|
+
def supports_scrubbing
|
56
|
+
true
|
57
|
+
end
|
58
|
+
|
59
|
+
def scrub(transcript)
|
60
|
+
transcript.
|
61
|
+
gsub(%r((Authorization: Basic )\w+), '\1[FILTERED]').
|
62
|
+
gsub(%r((<ewayCardNumber>)\d+(</ewayCardNumber>))i, '\1[FILTERED]\2').
|
63
|
+
gsub(%r((<ewayCVN>)\d+(</ewayCVN>))i, '\1[FILTERED]\2')
|
64
|
+
end
|
65
|
+
|
55
66
|
private
|
56
67
|
def requires_address!(options)
|
57
68
|
raise ArgumentError.new("Missing eWay required parameters: address or billing_address") unless (options.has_key?(:address) or options.has_key?(:billing_address))
|
@@ -169,6 +169,17 @@ module ActiveMerchant #:nodoc:
|
|
169
169
|
commit(url_for("Transaction"), params)
|
170
170
|
end
|
171
171
|
|
172
|
+
def supports_scrubbing
|
173
|
+
true
|
174
|
+
end
|
175
|
+
|
176
|
+
def scrub(transcript)
|
177
|
+
transcript.
|
178
|
+
gsub(%r((Authorization: Basic )\w+), '\1[FILTERED]').
|
179
|
+
gsub(%r(("Number\\?":\\?")[^"]*)i, '\1[FILTERED]').
|
180
|
+
gsub(%r(("CVN\\?":\\?"?)[^",]*)i, '\1[FILTERED]')
|
181
|
+
end
|
182
|
+
|
172
183
|
private
|
173
184
|
|
174
185
|
def add_metadata(params, options)
|
@@ -0,0 +1,238 @@
|
|
1
|
+
require 'json'
|
2
|
+
|
3
|
+
module ActiveMerchant #:nodoc:
|
4
|
+
module Billing #:nodoc:
|
5
|
+
class ForteGateway < Gateway
|
6
|
+
self.test_url = 'https://sandbox.forte.net/api/v2'
|
7
|
+
self.live_url = 'https://api.forte.net/v2'
|
8
|
+
|
9
|
+
self.supported_countries = ['US']
|
10
|
+
self.default_currency = 'USD'
|
11
|
+
self.supported_cardtypes = [:visa, :master, :american_express, :discover]
|
12
|
+
|
13
|
+
self.homepage_url = 'https://www.forte.net'
|
14
|
+
self.display_name = 'Forte'
|
15
|
+
|
16
|
+
def initialize(options={})
|
17
|
+
requires!(options, :api_key, :secret, :location_id, :account_id)
|
18
|
+
super
|
19
|
+
end
|
20
|
+
|
21
|
+
def purchase(money, payment_method, options={})
|
22
|
+
post = {}
|
23
|
+
add_amount(post, money, options)
|
24
|
+
add_payment_method(post, payment_method)
|
25
|
+
add_billing_address(post, options)
|
26
|
+
add_shipping_address(post, options)
|
27
|
+
post[:action] = "sale"
|
28
|
+
|
29
|
+
commit(:post, post)
|
30
|
+
end
|
31
|
+
|
32
|
+
def authorize(money, payment_method, options={})
|
33
|
+
post = {}
|
34
|
+
add_amount(post, money, options)
|
35
|
+
add_payment_method(post, payment_method)
|
36
|
+
add_billing_address(post, options)
|
37
|
+
add_shipping_address(post, options)
|
38
|
+
post[:action] = "authorize"
|
39
|
+
|
40
|
+
commit(:post, post)
|
41
|
+
end
|
42
|
+
|
43
|
+
def capture(money, authorization, options={})
|
44
|
+
post = {}
|
45
|
+
post[:transaction_id] = transaction_id_from(authorization)
|
46
|
+
post[:authorization_code] = authorization_code_from(authorization)
|
47
|
+
post[:action] = "capture"
|
48
|
+
|
49
|
+
commit(:put, post)
|
50
|
+
end
|
51
|
+
|
52
|
+
def credit(money, payment_method, options={})
|
53
|
+
post = {}
|
54
|
+
add_amount(post, money, options)
|
55
|
+
add_payment_method(post, payment_method)
|
56
|
+
add_billing_address(post, options)
|
57
|
+
post[:action] = "disburse"
|
58
|
+
|
59
|
+
commit(:post, post)
|
60
|
+
end
|
61
|
+
|
62
|
+
def void(authorization, options={})
|
63
|
+
post = {}
|
64
|
+
post[:transaction_id] = transaction_id_from(authorization)
|
65
|
+
post[:authorization_code] = authorization_code_from(authorization)
|
66
|
+
post[:action] = "void"
|
67
|
+
|
68
|
+
commit(:put, post)
|
69
|
+
end
|
70
|
+
|
71
|
+
def verify(credit_card, options={})
|
72
|
+
MultiResponse.run(:use_first_response) do |r|
|
73
|
+
r.process { authorize(100, credit_card, options) }
|
74
|
+
r.process(:ignore_result) { void(r.authorization, options) }
|
75
|
+
end
|
76
|
+
end
|
77
|
+
|
78
|
+
def supports_scrubbing?
|
79
|
+
true
|
80
|
+
end
|
81
|
+
|
82
|
+
def scrub(transcript)
|
83
|
+
transcript.
|
84
|
+
gsub(%r((Authorization: Basic )\w+), '\1[FILTERED]').
|
85
|
+
gsub(%r((account_number)\W+\d+), '\1[FILTERED]').
|
86
|
+
gsub(%r((card_verification_value)\W+\d+), '\1[FILTERED]')
|
87
|
+
end
|
88
|
+
|
89
|
+
private
|
90
|
+
|
91
|
+
def add_auth(post)
|
92
|
+
post[:account_id] = "act_#{@options[:account_id]}"
|
93
|
+
post[:location_id] = "loc_#{@options[:location_id]}"
|
94
|
+
end
|
95
|
+
|
96
|
+
def add_amount(post, money, options)
|
97
|
+
post[:authorization_amount] = amount(money)
|
98
|
+
end
|
99
|
+
|
100
|
+
def add_billing_address(post, options)
|
101
|
+
if address = options[:billing_address] || options[:address]
|
102
|
+
post[:billing_address] = {}
|
103
|
+
post[:billing_address][:first_name] = address[:name].split(" ").first if address[:name]
|
104
|
+
post[:billing_address][:last_name] = address[:name].split(" ").last if address[:name]
|
105
|
+
post[:billing_address][:address_line1] = address[:address1] if address[:address1]
|
106
|
+
post[:billing_address][:address_line2] = address[:address2] if address[:address2]
|
107
|
+
post[:billing_address][:address_country] = address[:country] if address[:country]
|
108
|
+
post[:billing_address][:address_zip] = address[:zip] if address[:zip]
|
109
|
+
post[:billing_address][:address_state] = address[:state] if address[:state]
|
110
|
+
post[:billing_address][:address_city] = address[:city] if address[:city]
|
111
|
+
end
|
112
|
+
end
|
113
|
+
|
114
|
+
def add_shipping_address(post, options)
|
115
|
+
return unless options[:shipping_address]
|
116
|
+
address = options[:shipping_address]
|
117
|
+
|
118
|
+
post[:shipping_address] = {}
|
119
|
+
post[:shipping_address][:first_name] = address[:name].split(" ").first if address[:name]
|
120
|
+
post[:shipping_address][:last_name] = address[:name].split(" ").last if address[:name]
|
121
|
+
post[:shipping_address][:address_line1] = address[:address1] if address[:address1]
|
122
|
+
post[:shipping_address][:address_line2] = address[:address2] if address[:address2]
|
123
|
+
post[:shipping_address][:address_country] = address[:country] if address[:country]
|
124
|
+
post[:shipping_address][:address_zip] = address[:zip] if address[:zip]
|
125
|
+
post[:shipping_address][:address_state] = address[:state] if address[:state]
|
126
|
+
post[:shipping_address][:address_city] = address[:city] if address[:city]
|
127
|
+
end
|
128
|
+
|
129
|
+
def add_payment_method(post, payment_method)
|
130
|
+
if payment_method.respond_to?(:brand)
|
131
|
+
add_credit_card(post, payment_method)
|
132
|
+
else
|
133
|
+
add_echeck(post, payment_method)
|
134
|
+
end
|
135
|
+
end
|
136
|
+
|
137
|
+
def add_echeck(post, payment)
|
138
|
+
post[:echeck] = {}
|
139
|
+
post[:echeck][:account_holder] = payment.name
|
140
|
+
post[:echeck][:account_number] = payment.account_number
|
141
|
+
post[:echeck][:routing_number] = payment.routing_number
|
142
|
+
post[:echeck][:account_type] = payment.account_type
|
143
|
+
post[:echeck][:check_number] = payment.number
|
144
|
+
end
|
145
|
+
|
146
|
+
def add_credit_card(post, payment)
|
147
|
+
post[:card] = {}
|
148
|
+
post[:card][:card_type] = format_card_brand(payment.brand)
|
149
|
+
post[:card][:name_on_card] = payment.name
|
150
|
+
post[:card][:account_number] = payment.number
|
151
|
+
post[:card][:expire_month] = payment.month
|
152
|
+
post[:card][:expire_year] = payment.year
|
153
|
+
post[:card][:card_verification_value] = payment.verification_value
|
154
|
+
end
|
155
|
+
|
156
|
+
def commit(type, parameters)
|
157
|
+
add_auth(parameters)
|
158
|
+
|
159
|
+
url = (test? ? test_url : live_url)
|
160
|
+
response = parse(handle_resp(raw_ssl_request(type, url + endpoint, parameters.to_json, headers)))
|
161
|
+
|
162
|
+
Response.new(
|
163
|
+
success_from(response),
|
164
|
+
message_from(response),
|
165
|
+
response,
|
166
|
+
authorization: authorization_from(response),
|
167
|
+
avs_result: AVSResult.new(code: response["response"]["avs_result"]),
|
168
|
+
cvv_result: CVVResult.new(response["response"]["cvv_code"]),
|
169
|
+
test: test?
|
170
|
+
)
|
171
|
+
end
|
172
|
+
|
173
|
+
def handle_resp(response)
|
174
|
+
case response.code.to_i
|
175
|
+
when 200..499
|
176
|
+
response.body
|
177
|
+
else
|
178
|
+
raise ResponseError.new(response)
|
179
|
+
end
|
180
|
+
end
|
181
|
+
|
182
|
+
def parse(response_body)
|
183
|
+
JSON.parse(response_body)
|
184
|
+
end
|
185
|
+
|
186
|
+
def success_from(response)
|
187
|
+
response["response"]["response_code"] == "A01"
|
188
|
+
end
|
189
|
+
|
190
|
+
def message_from(response)
|
191
|
+
response["response"]["response_desc"]
|
192
|
+
end
|
193
|
+
|
194
|
+
def authorization_from(response)
|
195
|
+
[response["transaction_id"], response["authorization_code"]].join("#")
|
196
|
+
end
|
197
|
+
|
198
|
+
def endpoint
|
199
|
+
"/accounts/act_#{@options[:account_id]}/locations/loc_#{@options[:location_id]}/transactions/"
|
200
|
+
end
|
201
|
+
|
202
|
+
def headers
|
203
|
+
{
|
204
|
+
'Authorization' => ("Basic " + Base64.strict_encode64("#{@options[:api_key]}:#{@options[:secret]}")),
|
205
|
+
'X-Forte-Auth-Account-Id' => "act_#{@options[:account_id]}",
|
206
|
+
'Content-Type' => 'application/json'
|
207
|
+
}
|
208
|
+
end
|
209
|
+
|
210
|
+
def format_card_brand(card_brand)
|
211
|
+
case card_brand
|
212
|
+
when 'visa'
|
213
|
+
return 'visa'
|
214
|
+
when 'master'
|
215
|
+
return 'mast'
|
216
|
+
when 'american_express'
|
217
|
+
return 'amex'
|
218
|
+
when 'discover'
|
219
|
+
return 'disc'
|
220
|
+
end
|
221
|
+
end
|
222
|
+
|
223
|
+
def split_authorization(authorization)
|
224
|
+
authorization.split("#")
|
225
|
+
end
|
226
|
+
|
227
|
+
def authorization_code_from(authorization)
|
228
|
+
_, authorization_code = split_authorization(authorization)
|
229
|
+
authorization_code
|
230
|
+
end
|
231
|
+
|
232
|
+
def transaction_id_from(authorization)
|
233
|
+
transaction_id, _ = split_authorization(authorization)
|
234
|
+
transaction_id
|
235
|
+
end
|
236
|
+
end
|
237
|
+
end
|
238
|
+
end
|
@@ -264,6 +264,17 @@ module ActiveMerchant #:nodoc:
|
|
264
264
|
commit(build_reference_request('VOID', nil, authorization, options), options)
|
265
265
|
end
|
266
266
|
|
267
|
+
def supports_scrubbing
|
268
|
+
true
|
269
|
+
end
|
270
|
+
|
271
|
+
def scrub(transcript)
|
272
|
+
transcript.
|
273
|
+
gsub(%r((Authorization: Basic )\w+), '\1[FILTERED]').
|
274
|
+
gsub(%r((<CardNumber>)\d+(</CardNumber>)), '\1[FILTERED]\2').
|
275
|
+
gsub(%r((<CV2>)\d+(</CV2>)), '\1[FILTERED]\2')
|
276
|
+
end
|
277
|
+
|
267
278
|
private
|
268
279
|
|
269
280
|
def build_purchase_request(type, money, creditcard, options)
|
@@ -99,6 +99,16 @@ module ActiveMerchant #:nodoc:
|
|
99
99
|
commit(money, build_credit_request('CREDIT', money, transaction_id, credit_card))
|
100
100
|
end
|
101
101
|
|
102
|
+
def supports_scrubbing
|
103
|
+
true
|
104
|
+
end
|
105
|
+
|
106
|
+
def scrub(transcript)
|
107
|
+
transcript.
|
108
|
+
gsub(%r((Authorization: Basic )\w+), '\1[FILTERED]').
|
109
|
+
gsub(%r((<CardNum>)\d+(</CardNum>)), '\1[FILTERED]\2').
|
110
|
+
gsub(%r((<CVV2>)\d+(</CVV2>)), '\1[FILTERED]\2')
|
111
|
+
end
|
102
112
|
|
103
113
|
private
|
104
114
|
|
@@ -272,4 +282,3 @@ module ActiveMerchant #:nodoc:
|
|
272
282
|
end
|
273
283
|
end
|
274
284
|
end
|
275
|
-
|
@@ -245,6 +245,17 @@ module ActiveMerchant #:nodoc:
|
|
245
245
|
refund(money, identification, options)
|
246
246
|
end
|
247
247
|
|
248
|
+
def supports_scrubbing
|
249
|
+
true
|
250
|
+
end
|
251
|
+
|
252
|
+
def scrub(transcript)
|
253
|
+
transcript.
|
254
|
+
gsub(%r((Authorization: Basic )\w+), '\1[FILTERED]').
|
255
|
+
gsub(%r((<cardnumber>)\d+(</cardnumber>))i, '\1[FILTERED]\2').
|
256
|
+
gsub(%r((<cvmvalue>)\d+(</cvmvalue>))i, '\1[FILTERED]\2')
|
257
|
+
end
|
258
|
+
|
248
259
|
private
|
249
260
|
# Commit the transaction by posting the XML file to the LinkPoint server
|
250
261
|
def commit(money, creditcard, options = {})
|
@@ -3,7 +3,7 @@ require 'nokogiri'
|
|
3
3
|
module ActiveMerchant #:nodoc:
|
4
4
|
module Billing #:nodoc:
|
5
5
|
class LitleGateway < Gateway
|
6
|
-
SCHEMA_VERSION = '
|
6
|
+
SCHEMA_VERSION = '9.4'
|
7
7
|
|
8
8
|
self.test_url = 'https://www.testlitle.com/sandbox/communicator/online'
|
9
9
|
self.live_url = 'https://payments.litle.com/vap/communicator/online'
|
@@ -196,6 +196,11 @@ module ActiveMerchant #:nodoc:
|
|
196
196
|
doc.expDate(exp_date(payment_method))
|
197
197
|
doc.cardValidationNum(payment_method.verification_value)
|
198
198
|
end
|
199
|
+
if payment_method.is_a?(NetworkTokenizationCreditCard)
|
200
|
+
doc.cardholderAuthentication do
|
201
|
+
doc.authenticationValue(payment_method.payment_cryptogram)
|
202
|
+
end
|
203
|
+
end
|
199
204
|
end
|
200
205
|
end
|
201
206
|
|
@@ -234,6 +239,8 @@ module ActiveMerchant #:nodoc:
|
|
234
239
|
def add_order_source(doc, payment_method, options)
|
235
240
|
if options[:order_source]
|
236
241
|
doc.orderSource(options[:order_source])
|
242
|
+
elsif payment_method.is_a?(NetworkTokenizationCreditCard)
|
243
|
+
doc.orderSource('applepay')
|
237
244
|
elsif payment_method.respond_to?(:track_data) && payment_method.track_data.present?
|
238
245
|
doc.orderSource('retail')
|
239
246
|
else
|
@@ -166,7 +166,7 @@ module ActiveMerchant #:nodoc:
|
|
166
166
|
end
|
167
167
|
|
168
168
|
def add_invoice(xml, options)
|
169
|
-
xml.tag! "invoiceNumber", options[:order_id].to_s.gsub(/[^\w]/, '')
|
169
|
+
xml.tag! "invoiceNumber", truncate(options[:order_id].to_s.gsub(/[^\w]/, ''), 8)
|
170
170
|
end
|
171
171
|
|
172
172
|
def add_amount(xml, money, tag = "amount")
|
@@ -0,0 +1,167 @@
|
|
1
|
+
module ActiveMerchant #:nodoc:
|
2
|
+
module Billing #:nodoc:
|
3
|
+
class MicropaymentGateway < Gateway
|
4
|
+
|
5
|
+
self.display_name = "micropayment"
|
6
|
+
self.homepage_url = "https://www.micropayment.de/"
|
7
|
+
|
8
|
+
self.test_url = self.live_url = "https://sipg.micropayment.de/public/creditcard/v1.5.2/nvp/"
|
9
|
+
|
10
|
+
self.supported_countries = %w(DE)
|
11
|
+
self.default_currency = "EUR"
|
12
|
+
self.money_format = :cents
|
13
|
+
self.supported_cardtypes = [:visa, :master, :american_express]
|
14
|
+
|
15
|
+
def initialize(options={})
|
16
|
+
requires!(options, :access_key)
|
17
|
+
super
|
18
|
+
end
|
19
|
+
|
20
|
+
def purchase(amount, payment_method, options={})
|
21
|
+
post = {}
|
22
|
+
add_invoice(post, amount, options)
|
23
|
+
add_payment_method(post, payment_method)
|
24
|
+
add_customer_data(post, options)
|
25
|
+
commit("shortTransactionPurchase", post)
|
26
|
+
end
|
27
|
+
|
28
|
+
def authorize(amount, payment_method, options={})
|
29
|
+
post = {}
|
30
|
+
add_invoice(post, amount, options)
|
31
|
+
add_payment_method(post, payment_method)
|
32
|
+
add_customer_data(post, options)
|
33
|
+
commit("shortTransactionAuthorization", post)
|
34
|
+
end
|
35
|
+
|
36
|
+
def capture(amount, authorization, options={})
|
37
|
+
post = {}
|
38
|
+
add_reference(post, authorization)
|
39
|
+
add_invoice(post, amount, options)
|
40
|
+
commit("transactionCapture", post)
|
41
|
+
end
|
42
|
+
|
43
|
+
def void(authorization, options={})
|
44
|
+
post = {}
|
45
|
+
add_reference(post, authorization)
|
46
|
+
commit("transactionReversal", post)
|
47
|
+
end
|
48
|
+
|
49
|
+
def refund(amount, authorization, options={})
|
50
|
+
post = {}
|
51
|
+
add_reference(post, authorization)
|
52
|
+
add_invoice(post, amount, options)
|
53
|
+
commit("transactionRefund", post)
|
54
|
+
end
|
55
|
+
|
56
|
+
def verify(credit_card, options={})
|
57
|
+
MultiResponse.run(:use_first_response) do |r|
|
58
|
+
r.process { authorize(250, credit_card, options) }
|
59
|
+
r.process(:ignore_result) { void(r.authorization, options) }
|
60
|
+
end
|
61
|
+
end
|
62
|
+
|
63
|
+
def supports_scrubbing?
|
64
|
+
true
|
65
|
+
end
|
66
|
+
|
67
|
+
def scrub(transcript)
|
68
|
+
transcript.
|
69
|
+
gsub(%r((accessKey=)\w+), '\1[FILTERED]').
|
70
|
+
gsub(%r((number=)\d+), '\1[FILTERED]').
|
71
|
+
gsub(%r((cvc2=)\d+), '\1[FILTERED]')
|
72
|
+
end
|
73
|
+
|
74
|
+
private
|
75
|
+
|
76
|
+
def add_invoice(post, money, options)
|
77
|
+
if money
|
78
|
+
post[:amount] = amount(money)
|
79
|
+
post[:currency] = options[:currency] || currency(money)
|
80
|
+
end
|
81
|
+
post[:project] = options[:project] || "sprdly"
|
82
|
+
end
|
83
|
+
|
84
|
+
def add_payment_method(post, payment_method)
|
85
|
+
post[:firstname] = payment_method.first_name
|
86
|
+
post[:surname] = payment_method.last_name
|
87
|
+
post[:number] = payment_method.number
|
88
|
+
post[:cvc2] = payment_method.verification_value
|
89
|
+
post[:expiryYear] = format(payment_method.year, :four_digits)
|
90
|
+
post[:expiryMonth] = format(payment_method.month, :two_digits)
|
91
|
+
end
|
92
|
+
|
93
|
+
def add_customer_data(post, options)
|
94
|
+
post[:email] = options[:email] if options[:email]
|
95
|
+
post[:ip] = options[:ip] || "1.1.1.1"
|
96
|
+
post[:sendMail] = options[:send_mail] || 'false'
|
97
|
+
end
|
98
|
+
|
99
|
+
def add_reference(post, authorization)
|
100
|
+
session_id, transaction_id = split_authorization(authorization)
|
101
|
+
post[:sessionId] = session_id
|
102
|
+
post[:transactionId] = transaction_id
|
103
|
+
end
|
104
|
+
|
105
|
+
def commit(action, params)
|
106
|
+
|
107
|
+
params[:testMode] = 1 if test?
|
108
|
+
params[:accessKey] = @options[:access_key]
|
109
|
+
|
110
|
+
response = parse(ssl_post(url(action), post_data(action, params), headers))
|
111
|
+
|
112
|
+
Response.new(
|
113
|
+
succeeded = success_from(response),
|
114
|
+
message_from(succeeded, response),
|
115
|
+
response,
|
116
|
+
authorization: authorization_from(response),
|
117
|
+
avs_result: AVSResult.new(code: response["some_avs_result_key"]),
|
118
|
+
cvv_result: CVVResult.new(response["some_cvv_result_key"]),
|
119
|
+
test: test?
|
120
|
+
)
|
121
|
+
end
|
122
|
+
|
123
|
+
def headers
|
124
|
+
{ "Content-Type" => "application/x-www-form-urlencoded;charset=UTF-8" }
|
125
|
+
end
|
126
|
+
|
127
|
+
def post_data(action, params)
|
128
|
+
params.map {|k, v| "#{k}=#{CGI.escape(v.to_s)}"}.join('&')
|
129
|
+
end
|
130
|
+
|
131
|
+
def url(action)
|
132
|
+
action_url = test? ? test_url : live_url
|
133
|
+
"#{action_url}?action=#{action}"
|
134
|
+
end
|
135
|
+
|
136
|
+
def parse(body)
|
137
|
+
body.split(/\r?\n/).inject({}) do |acc, pair|
|
138
|
+
key, value = pair.split("=")
|
139
|
+
acc[key] = CGI.unescape(value)
|
140
|
+
acc
|
141
|
+
end
|
142
|
+
end
|
143
|
+
|
144
|
+
def success_from(response)
|
145
|
+
response["error"] == "0" &&
|
146
|
+
response["transactionResultCode"] == "00" &&
|
147
|
+
response["transactionStatus"] == "SUCCESS"
|
148
|
+
end
|
149
|
+
|
150
|
+
def message_from(succeeded, response)
|
151
|
+
if succeeded
|
152
|
+
"Succeeded"
|
153
|
+
else
|
154
|
+
response["errorMessage"] || response["transactionResultMessage"]
|
155
|
+
end
|
156
|
+
end
|
157
|
+
|
158
|
+
def split_authorization(authorization)
|
159
|
+
authorization.split("|")
|
160
|
+
end
|
161
|
+
|
162
|
+
def authorization_from(response)
|
163
|
+
"#{response["sessionId"]}|#{response["transactionId"]}"
|
164
|
+
end
|
165
|
+
end
|
166
|
+
end
|
167
|
+
end
|