offsite_payments 2.7.21 → 2.7.28

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.
Files changed (29) hide show
  1. checksums.yaml +4 -4
  2. data/README.md +2 -1
  3. data/lib/offsite_payments.rb +1 -1
  4. data/lib/offsite_payments/integrations/a1agregator.rb +0 -8
  5. data/lib/offsite_payments/integrations/bit_pay.rb +1 -1
  6. data/lib/offsite_payments/integrations/citrus.rb +2 -2
  7. data/lib/offsite_payments/integrations/direc_pay.rb +1 -1
  8. data/lib/offsite_payments/integrations/easy_pay.rb +1 -1
  9. data/lib/offsite_payments/integrations/epay.rb +2 -2
  10. data/lib/offsite_payments/integrations/gestpay.rb +2 -2
  11. data/lib/offsite_payments/integrations/liqpay.rb +2 -2
  12. data/lib/offsite_payments/integrations/mollie_ideal.rb +1 -1
  13. data/lib/offsite_payments/integrations/mollie_mistercash.rb +1 -1
  14. data/lib/offsite_payments/integrations/pag_seguro.rb +1 -1
  15. data/lib/offsite_payments/integrations/paxum.rb +2 -2
  16. data/lib/offsite_payments/integrations/pay_fast.rb +1 -1
  17. data/lib/offsite_payments/integrations/payflow_link.rb +0 -4
  18. data/lib/offsite_payments/integrations/paytm.rb +2 -2
  19. data/lib/offsite_payments/integrations/payu_in.rb +3 -3
  20. data/lib/offsite_payments/integrations/platron.rb +1 -1
  21. data/lib/offsite_payments/integrations/quickpay.rb +1 -1
  22. data/lib/offsite_payments/integrations/quickpay_v10.rb +173 -0
  23. data/lib/offsite_payments/integrations/realex_offsite.rb +385 -21
  24. data/lib/offsite_payments/integrations/sage_pay_form.rb +1 -0
  25. data/lib/offsite_payments/integrations/universal.rb +0 -1
  26. data/lib/offsite_payments/integrations/web_pay.rb +1 -1
  27. data/lib/offsite_payments/integrations/webmoney.rb +1 -1
  28. data/lib/offsite_payments/version.rb +1 -1
  29. metadata +5 -3
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: 11d3af9b6ea7b963a53bba9b38c1c0495aa8a676a5d15a081fff92461ea7848c
4
- data.tar.gz: d68bbaabd36c6e31f4ccdd9c77245dfb8adc1596dd9e8b71ba2042f1de010760
3
+ metadata.gz: 7d6f15a62a3d0c2744b89d969b27b4211d3308edd81175447fd2c9609c191787
4
+ data.tar.gz: cb1dff98006362f1f80fb9d9957dff0e049d6a401658f4544c112f538de1c5ee
5
5
  SHA512:
6
- metadata.gz: 57c6f0dda0656e8a528eec91ff862d7580c2603559011d0ee2ddc7fbb437244ef2c3ee111fcf2b7a35ca34c68235a85debc77f33477b5bdb7b07beaa3b759db6
7
- data.tar.gz: 50b50027b8cd16ed325e3e12692f775d615d32f6caa187882e89dfedb10cbdc63c4170278e8ae20ddd5e5ea056c1feaa85292efe4290bb4066204d25825b68d5
6
+ metadata.gz: 572f3afcfb7d6d22cbf0097d778996d727091e831a534f1e1f9f6e7a2063cac9091588026ffb9430664138c906fadba86b4d52d7a6499bb7cdcc576d8ab22c3f
7
+ data.tar.gz: e0701df36a24581fa8530529f017e3eb550c4e76abab0ca74265637e5cf57109d6094c661f0fa7f92f29876b7388594d6ac744f980608f1193133b3bb75ac516
data/README.md CHANGED
@@ -1,5 +1,5 @@
1
1
  # Offsite Payments
2
- [![Build Status](https://travis-ci.org/activemerchant/offsite_payments.svg?branch=master)](https://travis-ci.org/activemerchant/offsite_payments)
2
+ [![Build Status](https://github.com/activemerchant/offsite_payments/workflows/CI/badge.svg?branch=master)](https://github.com/activemerchant/offsite_payments/actions?query=workflow%3ACI)
3
3
  [![Code Climate](https://codeclimate.com/github/activemerchant/offsite_payments/badges/gpa.svg)](https://codeclimate.com/github/activemerchant/offsite_payments)
4
4
 
5
5
  Offsite Payments is an extraction from the ecommerce system [Shopify](http://www.shopify.com). Shopify's requirements for a simple and unified API to handle dozens of different offsite payment pages (often called hosted payment pages) with very different exposed APIs was the chief principle in designing the library.
@@ -78,6 +78,7 @@ one.
78
78
  * [PayDollar](http://www.paydollar.com)
79
79
  * [Paysbuy](https://www.paysbuy.com/) - TH
80
80
  * [Platron](https://www.platron.ru/) - RU
81
+ * [QuickPay](http://quickpay.net/dk/) - AT, DE, DK, EE, LT, LV, FO, NL, NO, SE, UK
81
82
  * [RBK Money](https://rbkmoney.ru/) - RU
82
83
  * [Robokassa](http://robokassa.ru/) - RU
83
84
  * [SagePay Form](http://www.sagepay.com/products_services/sage_pay_go/integration/form)
@@ -40,5 +40,5 @@ module OffsitePayments
40
40
  self.mode == :test
41
41
  end
42
42
 
43
- CURRENCIES_WITHOUT_FRACTIONS = [ 'BIF', 'BYR', 'CLP', 'CVE', 'DJF', 'GNF', 'HUF', 'ISK', 'JPY', 'KMF', 'KRW', 'PYG', 'RWF', 'TWD', 'UGX', 'VND', 'VUV', 'XAF', 'XOF', 'XPF' ]
43
+ CURRENCIES_WITHOUT_FRACTIONS = [ 'BIF', 'BYR', 'CLP', 'CVE', 'DJF', 'GNF', 'ISK', 'JPY', 'KMF', 'KRW', 'PYG', 'RWF', 'TWD', 'UGX', 'VND', 'VUV', 'XAF', 'XOF', 'XPF' ]
44
44
  end
@@ -93,14 +93,6 @@ module OffsitePayments #:nodoc:
93
93
  params['type']
94
94
  end
95
95
 
96
- def partner_income
97
- params['partner_income']
98
- end
99
-
100
- def system_income
101
- params['system_income']
102
- end
103
-
104
96
  # Additional notification request params:
105
97
  # tid
106
98
  # name
@@ -41,7 +41,7 @@ module OffsitePayments #:nodoc:
41
41
  add_field('fullNotifications', true)
42
42
  add_field('transactionSpeed', 'high')
43
43
  add_field('token', account)
44
- end
44
+ end
45
45
 
46
46
  mapping :amount, 'price'
47
47
  mapping :order, 'orderID'
@@ -119,7 +119,7 @@ module OffsitePayments
119
119
  end
120
120
 
121
121
  def amount
122
- Money.from_amount(BigDecimal.new(gross), currency)
122
+ Money.from_amount(BigDecimal(gross), currency)
123
123
  end
124
124
 
125
125
  def transaction_id
@@ -202,7 +202,7 @@ module OffsitePayments
202
202
  end
203
203
 
204
204
  def status( order_id, order_amount )
205
- if @notification.invoice_ok?( order_id ) && @notification.amount_ok?( BigDecimal.new(order_amount) )
205
+ if @notification.invoice_ok?( order_id ) && @notification.amount_ok?(BigDecimal(order_amount))
206
206
  @notification.status
207
207
  else
208
208
  'Mismatch'
@@ -320,7 +320,7 @@ module OffsitePayments #:nodoc:
320
320
  data = ActiveUtils::PostData.new
321
321
  data[:requestparams] = parameters.join('|')
322
322
 
323
- response = ssl_get("#{url}?#{data.to_post_data}")
323
+ ssl_get("#{url}?#{data.to_post_data}")
324
324
  end
325
325
 
326
326
  def test?
@@ -101,7 +101,7 @@ module OffsitePayments #:nodoc:
101
101
  end
102
102
 
103
103
  def amount
104
- Money.from_amount(BigDecimal.new(gross), currency)
104
+ Money.from_amount(BigDecimal(gross), currency)
105
105
  end
106
106
 
107
107
  def item_id
@@ -125,7 +125,7 @@ module OffsitePayments #:nodoc:
125
125
  return false
126
126
  end
127
127
 
128
- %w(txnid orderid currency date time hash fraud payercountry issuercountry txnfee subscriptionid paymenttype cardno).each do |attr|
128
+ %w(txnid orderid date time hash fraud payercountry issuercountry txnfee subscriptionid paymenttype cardno).each do |attr|
129
129
  define_method(attr) do
130
130
  params[attr]
131
131
  end
@@ -138,7 +138,7 @@ module OffsitePayments #:nodoc:
138
138
  def generate_md5string
139
139
  md5string = String.new
140
140
  for line in @raw.split('&')
141
- key, value = *line.scan( %r{^([A-Za-z0-9_.]+)\=(.*)$} ).flatten
141
+ key, _ = *line.scan( %r{^([A-Za-z0-9_.]+)\=(.*)$} ).flatten
142
142
  md5string += params[key] if key != 'hash'
143
143
  end
144
144
  return md5string + @options[:credential3]
@@ -4,7 +4,7 @@ module OffsitePayments #:nodoc:
4
4
  module Integrations #:nodoc:
5
5
  module Gestpay
6
6
  mattr_accessor :service_url
7
- self.service_url = 'https://ecomm.sella.it/gestpay/pagam.asp'
7
+ self.service_url = 'https://ecomm.sella.it/pagam/pagam.aspx'
8
8
 
9
9
  def self.notification(post, options = {})
10
10
  Notification.new(post)
@@ -189,7 +189,7 @@ module OffsitePayments #:nodoc:
189
189
  response = ssl_get(Gestpay.service_url, decryption_query_string(shop_login, encrypted_string))
190
190
  encoded_response = parse_response(response)
191
191
  parse_delimited_string(encoded_response, DELIMITER, true)
192
- rescue GestpayEncryptionResponseError => e
192
+ rescue GestpayEncryptionResponseError
193
193
  { 'PAY1_TRANSACTIONRESULT' => 'Error' }
194
194
  end
195
195
 
@@ -80,7 +80,7 @@ module OffsitePayments #:nodoc:
80
80
  end
81
81
 
82
82
  def amount
83
- Money.from_amount(BigDecimal.new(gross), currency)
83
+ Money.from_amount(BigDecimal(gross), currency)
84
84
  end
85
85
 
86
86
  def item_id
@@ -156,7 +156,7 @@ module OffsitePayments #:nodoc:
156
156
  end
157
157
 
158
158
  def amount
159
- BigDecimal.new(gross)
159
+ BigDecimal(gross)
160
160
  end
161
161
 
162
162
  def item_id
@@ -133,7 +133,7 @@ module OffsitePayments #:nodoc:
133
133
  end
134
134
 
135
135
  def gross_cents
136
- (BigDecimal.new(@params['amount'], 2) * 100).to_i
136
+ (BigDecimal(@params['amount'], 2) * 100).to_i
137
137
  end
138
138
 
139
139
  def status
@@ -100,7 +100,7 @@ module OffsitePayments #:nodoc:
100
100
  end
101
101
 
102
102
  def gross_cents
103
- (BigDecimal.new(@params['amount'], 2) * 100).to_i
103
+ (BigDecimal(@params['amount'], 2) * 100).to_i
104
104
  end
105
105
 
106
106
  def status
@@ -111,7 +111,7 @@ module OffsitePayments #:nodoc:
111
111
  check_for_errors(response, xml)
112
112
 
113
113
  extract_token(xml)
114
- rescue Timeout::Error, Errno::ECONNRESET, Errno::ETIMEDOUT => e
114
+ rescue Timeout::Error, Errno::ECONNRESET, Errno::ETIMEDOUT
115
115
  raise ActionViewHelperError, "Erro ao conectar-se ao PagSeguro. Por favor, tente novamente."
116
116
  end
117
117
 
@@ -34,9 +34,9 @@ module OffsitePayments #:nodoc:
34
34
 
35
35
  module Common
36
36
  def generate_signature_string
37
- @raw_post.slice!(0) if @raw_post.starts_with?("&")
37
+ @raw_post.slice!(0) if @raw_post.start_with?("&")
38
38
  @raw_post = CGI.unescape(@raw_post)
39
- @raw_post = "&#{@raw_post}" unless @raw_post.starts_with?("&")
39
+ @raw_post = "&#{@raw_post}" unless @raw_post.start_with?("&")
40
40
  arr = @raw_post.split('&')
41
41
  arr.delete(arr.last)
42
42
  data = arr.join('&')
@@ -212,7 +212,7 @@ module OffsitePayments #:nodoc:
212
212
 
213
213
  # The net amount credited to the receiver's account.
214
214
  def amount
215
- Money.from_amount(BigDecimal.new(params['amount_net']), currency)
215
+ Money.from_amount(BigDecimal(params['amount_net']), currency)
216
216
  end
217
217
 
218
218
  # The name of the item being charged for.
@@ -138,10 +138,6 @@ module OffsitePayments #:nodoc:
138
138
  nil
139
139
  end
140
140
 
141
- def status
142
- params['RESPMSG']
143
- end
144
-
145
141
  # Id of this transaction (paypal number)
146
142
  def transaction_id
147
143
  params['PNREF']
@@ -136,7 +136,7 @@ module OffsitePayments #:nodoc:
136
136
 
137
137
  # Order amount should be equal to gross
138
138
  def amount_ok?(order_amount)
139
- BigDecimal.new(original_gross) == order_amount
139
+ BigDecimal(original_gross) == order_amount
140
140
  end
141
141
 
142
142
  # Status of transaction return from the Paytm. List of possible values:
@@ -245,7 +245,7 @@ module OffsitePayments #:nodoc:
245
245
  end
246
246
 
247
247
  def status(order_id, order_amount)
248
- if @notification.invoice_ok?(order_id) && @notification.amount_ok?(BigDecimal.new(order_amount))
248
+ if @notification.invoice_ok?(order_id) && @notification.amount_ok?(BigDecimal(order_amount))
249
249
  @notification.status
250
250
  else
251
251
  'Mismatch'
@@ -116,9 +116,9 @@ module OffsitePayments #:nodoc:
116
116
  end
117
117
 
118
118
  # Order amount should be equal to gross - discount
119
- def amount_ok?( order_amount, order_discount = BigDecimal.new( '0.0' ) )
119
+ def amount_ok?( order_amount, order_discount = BigDecimal( '0.0' ) )
120
120
  parsed_discount = discount.nil? ? 0.to_d : discount.to_d
121
- BigDecimal.new( original_gross ) == order_amount && parsed_discount == order_discount
121
+ BigDecimal( original_gross ) == order_amount && parsed_discount == order_discount
122
122
  end
123
123
 
124
124
  # Status of transaction return from the PayU. List of possible values:
@@ -258,7 +258,7 @@ module OffsitePayments #:nodoc:
258
258
  end
259
259
 
260
260
  def status( order_id, order_amount )
261
- if @notification.invoice_ok?( order_id ) && @notification.amount_ok?( BigDecimal.new(order_amount) )
261
+ if @notification.invoice_ok?( order_id ) && @notification.amount_ok?( BigDecimal(order_amount) )
262
262
  @notification.status
263
263
  else
264
264
  'Mismatch'
@@ -120,7 +120,7 @@ module OffsitePayments #:nodoc:
120
120
  end
121
121
 
122
122
  def amount
123
- Money.from_amount(BigDecimal.new(params['pg_amount']), currency)
123
+ Money.from_amount(BigDecimal(params['pg_amount']), currency)
124
124
  end
125
125
 
126
126
  def secret
@@ -2,7 +2,7 @@ module OffsitePayments #:nodoc:
2
2
  module Integrations #:nodoc:
3
3
  module Quickpay
4
4
  mattr_accessor :service_url
5
- self.service_url = 'https://secure.quickpay.dk/form/'
5
+ self.service_url = 'https://legacy-proxy.quickpay.net/form/'
6
6
 
7
7
  def self.notification(post, options = {})
8
8
  Notification.new(post, options)
@@ -0,0 +1,173 @@
1
+ require 'openssl'
2
+
3
+ module OffsitePayments #:nodoc:
4
+ module Integrations #:nodoc:
5
+ module QuickpayV10
6
+ mattr_accessor :service_url
7
+ self.service_url = 'https://payment.quickpay.net'
8
+
9
+ def self.notification(post, options = {})
10
+ Notification.new(post)
11
+ end
12
+
13
+ def self.return(post, options = {})
14
+ Return.new(post, options)
15
+ end
16
+
17
+ # credential2: Payment window API key
18
+ class Helper < OffsitePayments::Helper
19
+ def initialize(order, account, options = {})
20
+ payment_window_api_key options.delete(:credential2)
21
+ super
22
+ add_field('version', 'v10')
23
+ add_field('type', 'payment')
24
+ add_field('language', 'da')
25
+ add_field('autocapture', 0)
26
+ add_field('order_id', format_order_number(order))
27
+ end
28
+
29
+ def payment_window_api_key(value)
30
+ @payment_window_api_key = value
31
+ end
32
+
33
+ def form_fields
34
+ @fields.merge('checksum' => generate_checksum)
35
+ end
36
+
37
+ def flatten_params(obj, result = {}, path = [])
38
+ case obj
39
+ when Hash
40
+ obj.each do |k, v|
41
+ flatten_params(v, result, [*path, k])
42
+ end
43
+ when Array
44
+ obj.each_with_index do |v, i|
45
+ flatten_params(v, result, [*path, i])
46
+ end
47
+ else
48
+ result[path.map{|p| "[#{p}]"}.join.to_sym] = obj
49
+ end
50
+ result
51
+ end
52
+
53
+ def generate_checksum
54
+ flattened_params = flatten_params(@fields)
55
+ values = flattened_params.sort.map { |_, value| value }
56
+ base = values.join(' ')
57
+ OpenSSL::HMAC.hexdigest('sha256', @payment_window_api_key, base)
58
+ end
59
+
60
+ # Limited to 20 digits max
61
+ def format_order_number(number)
62
+ number.to_s.gsub(/[^\w]/, '').rjust(4, "0")[0...20]
63
+ end
64
+
65
+ mapping :version, 'version'
66
+ mapping :type, 'type'
67
+ mapping :account, 'merchant_id'
68
+ mapping :language, 'language'
69
+ mapping :amount, 'amount'
70
+ mapping :currency, 'currency'
71
+
72
+ mapping :return_url, 'continueurl'
73
+ mapping :cancel_return_url, 'cancelurl'
74
+ mapping :notify_url, 'callbackurl'
75
+
76
+ mapping :autocapture, 'autocapture'
77
+ mapping :autofee, 'autofee'
78
+
79
+ mapping :description, 'description'
80
+ mapping :payment_methods, 'payment_methods'
81
+ mapping :acquirer, 'acquirer'
82
+ mapping :branding_id, 'branding_id'
83
+ mapping :google_analytics_tracking_id, 'google_analytics_tracking_id'
84
+ mapping :google_analytics_client_id, 'google_analytics_client_id'
85
+ mapping :variables, 'variables'
86
+ mapping :text_on_statement, 'text_on_statement'
87
+ mapping :customer_email, 'customer_email'
88
+
89
+ mapping :splitpayment, 'splitpayment'
90
+ mapping :forcemobile, 'forcemobile'
91
+ mapping :deadline, 'deadline'
92
+ mapping :cardhash, 'cardhash'
93
+
94
+ mapping :invoice_address, {}
95
+ mapping :billing_address, {}
96
+ end
97
+
98
+ # credential3: private key
99
+ # checksum_header: QuickPay-Checksum-Sha256 request header value
100
+ class Notification < OffsitePayments::Notification
101
+ # http://tech.quickpay.net/appendixes/errors/
102
+ def complete?
103
+ status == '20000'
104
+ end
105
+
106
+ def item_id
107
+ params['order_id']
108
+ end
109
+
110
+ def transaction_id
111
+ params['id']
112
+ end
113
+
114
+ def received_at
115
+ Time.iso8601(params['created_at'])
116
+ end
117
+
118
+ def gross
119
+ "%.2f" % (gross_cents / 100.0)
120
+ end
121
+
122
+ def gross_cents
123
+ last_operation['amount']
124
+ end
125
+
126
+ def last_operation
127
+ params['operations'].last
128
+ end
129
+
130
+ def status
131
+ last_operation['qp_status_code'] if last_operation
132
+ end
133
+
134
+ # Provide access to raw fields from quickpay
135
+ %w(
136
+ accepted
137
+ test_mode
138
+ branding_id
139
+ variables
140
+ acquirer
141
+ operations
142
+ metadata
143
+ balance
144
+ currency
145
+ ).each do |attr|
146
+ define_method(attr) do
147
+ params[attr]
148
+ end
149
+ end
150
+
151
+ def generate_checksum
152
+ OpenSSL::HMAC.hexdigest('sha256', @options[:credential3], @raw)
153
+ end
154
+
155
+ def checksum_header
156
+ @options[:checksum_header]
157
+ end
158
+
159
+ # Quickpay doesn't do acknowledgements of callback notifications
160
+ # Instead it provides a SHA256 checksum header
161
+ def acknowledge(authcode = nil)
162
+ generate_checksum == checksum_header
163
+ end
164
+
165
+ # Take the posted data and move the relevant data into a hash
166
+ def parse(post)
167
+ @raw = post.to_s
168
+ @params = JSON.parse(post)
169
+ end
170
+ end
171
+ end
172
+ end
173
+ end
@@ -141,6 +141,256 @@ module OffsitePayments #:nodoc:
141
141
  'WY' => 'Wyoming'
142
142
  }
143
143
 
144
+ COUNTRY_PHONE_NUMBERS = {
145
+ 'AD' => { :code => '376', :length => [6, 7, 8, 9] },
146
+ 'AE' => { :code => '971', :length => [7, 8, 9] },
147
+ 'AF' => { :code => '93', :length => [8, 9] },
148
+ 'AG' => { :code => '1', :length => [10] },
149
+ 'AI' => { :code => '1', :length => [10] },
150
+ 'AL' => { :code => '355', :length => [7, 8, 9] },
151
+ 'AM' => { :code => '374', :length => [8] },
152
+ 'AO' => { :code => '244', :length => [9] },
153
+ 'AQ' => { :code => '672', :length => [] },
154
+ 'AR' => { :code => '54', :length => [8, 9] },
155
+ 'AS' => { :code => '1', :length => [10] },
156
+ 'AT' => { :code => '43', :length => [7, 8, 9, 10, 11, 12, 13] },
157
+ 'AU' => { :code => '61', :length => [9] },
158
+ 'AW' => { :code => '297', :length => [7] },
159
+ 'AX' => { :code => '358', :length => [] },
160
+ 'AZ' => { :code => '994', :length => [8, 9] },
161
+ 'BA' => { :code => '387', :length => [8] },
162
+ 'BB' => { :code => '1', :length => [10] },
163
+ 'BD' => { :code => '880', :length => [10] },
164
+ 'BE' => { :code => '32', :length => [8, 9] },
165
+ 'BF' => { :code => '226', :length => [8] },
166
+ 'BG' => { :code => '359', :length => [8, 9, 10] },
167
+ 'BH' => { :code => '973', :length => [8] },
168
+ 'BI' => { :code => '257', :length => [8] },
169
+ 'BJ' => { :code => '229', :length => [8] },
170
+ 'BL' => { :code => '590', :length => [] },
171
+ 'BM' => { :code => '1', :length => [10] },
172
+ 'BN' => { :code => '673', :length => [7] },
173
+ 'BO' => { :code => '591', :length => [8] },
174
+ 'BQ' => { :code => '599', :length => [7] },
175
+ 'BR' => { :code => '55', :length => [10, 11] },
176
+ 'BS' => { :code => '1', :length => [10] },
177
+ 'BT' => { :code => '975', :length => [7, 8] },
178
+ 'BV' => { :code => '47', :length => [] },
179
+ 'BW' => { :code => '267', :length => [7] },
180
+ 'BY' => { :code => '375', :length => [9] },
181
+ 'BZ' => { :code => '501', :length => [7] },
182
+ 'CA' => { :code => '1', :length => [10] },
183
+ 'CC' => { :code => '61', :length => [9] },
184
+ 'CD' => { :code => '243', :length => [8] },
185
+ 'CF' => { :code => '236', :length => [8] },
186
+ 'CG' => { :code => '242', :length => [7] },
187
+ 'CH' => { :code => '41', :length => [9, 10] },
188
+ 'CI' => { :code => '225', :length => [8] },
189
+ 'CK' => { :code => '682', :length => [5] },
190
+ 'CL' => { :code => '56', :length => [8, 9] },
191
+ 'CM' => { :code => '237', :length => [8] },
192
+ 'CN' => { :code => '86', :length => [7, 8, 9, 10, 11] },
193
+ 'CO' => { :code => '57', :length => [9, 10] },
194
+ 'CR' => { :code => '506', :length => [8] },
195
+ 'CU' => { :code => '53', :length => [8] },
196
+ 'CV' => { :code => '238', :length => [7] },
197
+ 'CW' => { :code => '599', :length => [7] },
198
+ 'CX' => { :code => '61', :length => [] },
199
+ 'CY' => { :code => '357', :length => [8] },
200
+ 'CZ' => { :code => '420', :length => [9] },
201
+ 'DE' => { :code => '49', :length => [6, 7, 8, 9, 10, 11] },
202
+ 'DJ' => { :code => '253', :length => [6] },
203
+ 'DK' => { :code => '45', :length => [8] },
204
+ 'DM' => { :code => '1', :length => [10] },
205
+ 'DO' => { :code => '1', :length => [10] },
206
+ 'DZ' => { :code => '213', :length => [8] },
207
+ 'EC' => { :code => '593', :length => [8, 9] },
208
+ 'EE' => { :code => '372', :length => [7, 8] },
209
+ 'EG' => { :code => '20', :length => [9] },
210
+ 'EH' => { :code => '212', :length => [] },
211
+ 'ER' => { :code => '291', :length => [7] },
212
+ 'ES' => { :code => '34', :length => [9] },
213
+ 'ET' => { :code => '251', :length => [9] },
214
+ 'FI' => { :code => '358', :length => [9] },
215
+ 'FJ' => { :code => '679', :length => [7] },
216
+ 'FK' => { :code => '500', :length => [5] },
217
+ 'FM' => { :code => '691', :length => [7] },
218
+ 'FO' => { :code => '298', :length => [6] },
219
+ 'FR' => { :code => '33', :length => [9, 10] },
220
+ 'GA' => { :code => '241', :length => [6, 7, 8] },
221
+ 'GB' => { :code => '44', :length => [10, 11] },
222
+ 'GD' => { :code => '1', :length => [10] },
223
+ 'GE' => { :code => '995', :length => [9] },
224
+ 'GF' => { :code => '594', :length => [10] },
225
+ 'GG' => { :code => '44', :length => [] },
226
+ 'GH' => { :code => '233', :length => [5, 6, 7, 8] },
227
+ 'GI' => { :code => '350', :length => [8] },
228
+ 'GL' => { :code => '299', :length => [6] },
229
+ 'GM' => { :code => '220', :length => [7] },
230
+ 'GN' => { :code => '224', :length => [8] },
231
+ 'GP' => { :code => '590', :length => [10] },
232
+ 'GQ' => { :code => '240', :length => [6] },
233
+ 'GR' => { :code => '30', :length => [10] },
234
+ 'GS' => { :code => '500', :length => [] },
235
+ 'GT' => { :code => '502', :length => [8] },
236
+ 'GU' => { :code => '1', :length => [10] },
237
+ 'GW' => { :code => '245', :length => [7] },
238
+ 'GY' => { :code => '592', :length => [6, 7] },
239
+ 'HK' => { :code => '852', :length => [8] },
240
+ 'HN' => { :code => '504', :length => [7, 8] },
241
+ 'HR' => { :code => '385', :length => [8] },
242
+ 'HT' => { :code => '509', :length => [8] },
243
+ 'HU' => { :code => '36', :length => [8, 9] },
244
+ 'ID' => { :code => '62', :length => [8, 9, 10, 11] },
245
+ 'IE' => { :code => '353', :length => [9] },
246
+ 'IL' => { :code => '972', :length => [7, 8, 9] },
247
+ 'IM' => { :code => '44', :length => [] },
248
+ 'IN' => { :code => '91', :length => [10] },
249
+ 'IO' => { :code => '246', :length => [] },
250
+ 'IQ' => { :code => '964', :length => [8, 9, 10] },
251
+ 'IR' => { :code => '98', :length => [10] },
252
+ 'IS' => { :code => '354', :length => [7, 8, 9] },
253
+ 'IT' => { :code => '39', :length => [9, 11] },
254
+ 'JE' => { :code => '44', :length => [] },
255
+ 'JM' => { :code => '1', :length => [10] },
256
+ 'JO' => { :code => '962', :length => [8, 9] },
257
+ 'JP' => { :code => '81', :length => [9, 10] },
258
+ 'KE' => { :code => '254', :length => [9] },
259
+ 'KG' => { :code => '996', :length => [9] },
260
+ 'KH' => { :code => '855', :length => [8] },
261
+ 'KI' => { :code => '686', :length => [5] },
262
+ 'KM' => { :code => '269', :length => [7] },
263
+ 'KN' => { :code => '1', :length => [10] },
264
+ 'KP' => { :code => '850', :length => [8, 9] },
265
+ 'KR' => { :code => '82', :length => [8, 9] },
266
+ 'KW' => { :code => '965', :length => [7] },
267
+ 'KY' => { :code => '1', :length => [10] },
268
+ 'KZ' => { :code => '7', :length => [10] },
269
+ 'LA' => { :code => '856', :length => [8] },
270
+ 'LB' => { :code => '961', :length => [8] },
271
+ 'LC' => { :code => '1', :length => [10] },
272
+ 'LI' => { :code => '423', :length => [7] },
273
+ 'LK' => { :code => '94', :length => [10] },
274
+ 'LR' => { :code => '231', :length => [6, 7, 8] },
275
+ 'LS' => { :code => '266', :length => [8] },
276
+ 'LT' => { :code => '370', :length => [8] },
277
+ 'LU' => { :code => '352', :length => [9] },
278
+ 'LV' => { :code => '371', :length => [8] },
279
+ 'LY' => { :code => '218', :length => [8, 9] },
280
+ 'MA' => { :code => '212', :length => [8] },
281
+ 'MC' => { :code => '377', :length => [8, 9] },
282
+ 'MD' => { :code => '373', :length => [8] },
283
+ 'ME' => { :code => '382', :length => [8] },
284
+ 'MF' => { :code => '590', :length => [] },
285
+ 'MG' => { :code => '261', :length => [9] },
286
+ 'MH' => { :code => '692', :length => [7] },
287
+ 'MK' => { :code => '389', :length => [7, 8] },
288
+ 'ML' => { :code => '223', :length => [8] },
289
+ 'MM' => { :code => '95', :length => [7, 8] },
290
+ 'MN' => { :code => '976', :length => [7, 8, 9, 10] },
291
+ 'MO' => { :code => '853', :length => [8] },
292
+ 'MP' => { :code => '1', :length => [10] },
293
+ 'MQ' => { :code => '596', :length => [10] },
294
+ 'MR' => { :code => '222', :length => [7] },
295
+ 'MS' => { :code => '1', :length => [10] },
296
+ 'MT' => { :code => '356', :length => [8] },
297
+ 'MU' => { :code => '230', :length => [7] },
298
+ 'MV' => { :code => '960', :length => [7] },
299
+ 'MW' => { :code => '265', :length => [8] },
300
+ 'MX' => { :code => '52', :length => [8, 9, 10] },
301
+ 'MY' => { :code => '60', :length => [9, 10] },
302
+ 'MZ' => { :code => '258', :length => [8, 9] },
303
+ 'NA' => { :code => '264', :length => [6, 7] },
304
+ 'NC' => { :code => '687', :length => [6] },
305
+ 'NE' => { :code => '227', :length => [8] },
306
+ 'NF' => { :code => '672', :length => [6] },
307
+ 'NG' => { :code => '234', :length => [7, 8] },
308
+ 'NI' => { :code => '505', :length => [8] },
309
+ 'NL' => { :code => '31', :length => [9] },
310
+ 'NO' => { :code => '47', :length => [8] },
311
+ 'NP' => { :code => '977', :length => [7, 8] },
312
+ 'NR' => { :code => '674', :length => [7] },
313
+ 'NU' => { :code => '683', :length => [4] },
314
+ 'NZ' => { :code => '64', :length => [8, 9] },
315
+ 'OM' => { :code => '968', :length => [8] },
316
+ 'PA' => { :code => '507', :length => [7] },
317
+ 'PE' => { :code => '51', :length => [8, 9] },
318
+ 'PF' => { :code => '689', :length => [6] },
319
+ 'PG' => { :code => '675', :length => [7] },
320
+ 'PH' => { :code => '63', :length => [8, 9, 10] },
321
+ 'PK' => { :code => '92', :length => [9, 10] },
322
+ 'PL' => { :code => '48', :length => [9] },
323
+ 'PM' => { :code => '508', :length => [6] },
324
+ 'PN' => { :code => '64', :length => [9] },
325
+ 'PR' => { :code => '1', :length => [10] },
326
+ 'PS' => { :code => '970', :length => [8] },
327
+ 'PT' => { :code => '351', :length => [9] },
328
+ 'PW' => { :code => '680', :length => [7] },
329
+ 'PY' => { :code => '595', :length => [9] },
330
+ 'QA' => { :code => '974', :length => [7] },
331
+ 'RE' => { :code => '262', :length => [10] },
332
+ 'RO' => { :code => '40', :length => [9] },
333
+ 'RS' => { :code => '381', :length => [9] },
334
+ 'RU' => { :code => '7', :length => [10] },
335
+ 'RW' => { :code => '250', :length => [8, 9] },
336
+ 'SA' => { :code => '966', :length => [8, 9] },
337
+ 'SB' => { :code => '677', :length => [5] },
338
+ 'SC' => { :code => '248', :length => [6] },
339
+ 'SD' => { :code => '249', :length => [9] },
340
+ 'SE' => { :code => '46', :length => [9] },
341
+ 'SG' => { :code => '65', :length => [8, 9] },
342
+ 'SH' => { :code => '290', :length => [4] },
343
+ 'SI' => { :code => '386', :length => [8] },
344
+ 'SJ' => { :code => '47', :length => [8] },
345
+ 'SK' => { :code => '421', :length => [9] },
346
+ 'SL' => { :code => '232', :length => [8] },
347
+ 'SM' => { :code => '378', :length => [9, 10, 11, 12] },
348
+ 'SN' => { :code => '221', :length => [7] },
349
+ 'SO' => { :code => '252', :length => [7, 8] },
350
+ 'SR' => { :code => '597', :length => [6] },
351
+ 'SS' => { :code => '211', :length => [9] },
352
+ 'ST' => { :code => '239', :length => [6, 7] },
353
+ 'SV' => { :code => '503', :length => [8] },
354
+ 'SX' => { :code => '1', :length => [10] },
355
+ 'SY' => { :code => '963', :length => [7, 8] },
356
+ 'SZ' => { :code => '268', :length => [7] },
357
+ 'TC' => { :code => '1', :length => [10] },
358
+ 'TD' => { :code => '235', :length => [7] },
359
+ 'TF' => { :code => '262', :length => [] },
360
+ 'TG' => { :code => '228', :length => [7] },
361
+ 'TH' => { :code => '66', :length => [9, 10] },
362
+ 'TJ' => { :code => '992', :length => [9] },
363
+ 'TK' => { :code => '690', :length => [4] },
364
+ 'TL' => { :code => '670', :length => [7] },
365
+ 'TM' => { :code => '993', :length => [8] },
366
+ 'TN' => { :code => '216', :length => [8] },
367
+ 'TO' => { :code => '676', :length => [5, 6, 7] },
368
+ 'TR' => { :code => '90', :length => [10] },
369
+ 'TT' => { :code => '1', :length => [10] },
370
+ 'TV' => { :code => '688', :length => [5] },
371
+ 'TW' => { :code => '886', :length => [7, 8] },
372
+ 'TZ' => { :code => '255', :length => [9] },
373
+ 'UA' => { :code => '380', :length => [8, 9] },
374
+ 'UG' => { :code => '256', :length => [9] },
375
+ 'UM' => { :code => '1', :length => [] },
376
+ 'US' => { :code => '1', :length => [10] },
377
+ 'UY' => { :code => '598', :length => [7, 8] },
378
+ 'UZ' => { :code => '998', :length => [9] },
379
+ 'VA' => { :code => '39', :length => [9] },
380
+ 'VC' => { :code => '1', :length => [10] },
381
+ 'VE' => { :code => '58', :length => [10] },
382
+ 'VG' => { :code => '1', :length => [10] },
383
+ 'VI' => { :code => '1', :length => [10] },
384
+ 'VN' => { :code => '84', :length => [7, 8, 9, 10] },
385
+ 'VU' => { :code => '678', :length => [5, 6, 7] },
386
+ 'WF' => { :code => '681', :length => [6] },
387
+ 'WS' => { :code => '685', :length => [6, 7] },
388
+ 'YE' => { :code => '967', :length => [7, 8, 9] },
389
+ 'YT' => { :code => '262', :length => [7] },
390
+ 'ZA' => { :code => '27', :length => [9] },
391
+ 'ZM' => { :code => '260', :length => [9] },
392
+ 'ZW' => { :code => '263', :length => [8, 9, 10, 11] }
393
+ }
144
394
 
145
395
  def create_signature(fields, secret)
146
396
  data = fields.join('.')
@@ -171,27 +421,70 @@ module OffsitePayments #:nodoc:
171
421
  value.scan(/\d+/).join('')
172
422
  end
173
423
 
424
+ # This method is used for generating the "BILLING_CODE" field,
425
+ # which is only needed for US, CA and GB.
426
+ # This field is generated by concatenating the zip field and
427
+ # the first line of address with a pipe(|) between them
428
+ # if the country is GB, we remove the non-numeric characters
174
429
  def extract_avs_code(params={})
175
- [extract_digits(params[:zip]), extract_digits(params[:address1])].join('|')
430
+ country_code = lookup_country_code(params[:country], :alpha2)
431
+ return unless params[:zip] && params[:address1] && ['US', 'CA', 'GB'].include?(country_code)
432
+ code = [params[:zip], params[:address1]]
433
+ code = code.collect{|p| extract_digits(p) } if params[:country] == 'GB'
434
+ code = code.reject{|p| p.empty? }.join('|')
435
+ # Since this field accepts only a few characters, we remove the ones that are not accepted,
436
+ # and trim the white spaces
437
+ code = code.gsub(/[^a-z0-9_\-| ]+/i, '').strip
176
438
  end
177
439
 
178
440
  def extract_address_match_indicator(value)
179
441
  value ? 'TRUE' : 'FALSE'
180
442
  end
181
443
 
444
+ def adjust_phone_number_length(country_calling_code, phone_number)
445
+ country_calling_code[0...3] + '|' + phone_number[0...15]
446
+ end
447
+
182
448
  # The home phone number provided by the Cardholder. Should be In format:
183
449
  # of 'CountryCallingCode|Number' for example, '1|123456789'.
184
- def format_phone_number(phone_number)
450
+ def format_phone_number(phone_number, country_code)
185
451
  return nil if phone_number.nil?
186
452
 
187
- clean_number = phone_number.gsub(/\D/, '')
453
+ country_number = COUNTRY_PHONE_NUMBERS[country_code] || { :code => '0', :length => [] }
188
454
 
189
- return phone_number if clean_number.length < 10
455
+ # Remove non-digit characters
456
+ processed_number = phone_number.gsub(/\D/, '')
457
+ return '0|0' if [[], ['0']].include? processed_number.chars.uniq
190
458
 
191
- country_code = clean_number[0, clean_number.length - 9]
192
- number = clean_number[clean_number.length - 9, clean_number.length]
459
+ # Allow Italy and Ivory Coast to have leading zero, as they use it as a part of some phone numbers
460
+ if ['IT', 'CI'].include?(country_code) && /\A0[1-9]\d*/.match(processed_number)
461
+ return adjust_phone_number_length(country_number[:code], processed_number)
462
+ end
193
463
 
194
- "#{country_code}|#{number}"
464
+ return '0|0' if processed_number == country_number[:code]
465
+
466
+ # Remove leading zero(s)
467
+ processed_number = processed_number.gsub(/\A0*/, '')
468
+
469
+ # Check if the potential Singapore calling code is not the local prefix
470
+ if country_code == 'SG' &&
471
+ processed_number.start_with?(country_number[:code]) &&
472
+ country_number[:length].include?(processed_number.length)
473
+ then
474
+ return adjust_phone_number_length(country_number[:code], processed_number)
475
+ end
476
+
477
+ # Remove country calling code from the processed number and try to fix trivial mistakes
478
+ if processed_number.start_with?(country_number[:code]) ||
479
+ (!(country_number[:length].include?(processed_number.length)) &&
480
+ country_number[:length].include?(processed_number.length - country_number[:code].length) &&
481
+ (country_number[:code].chars.sort == processed_number[0...country_number[:code].length].chars.sort))
482
+ then
483
+ processed_number = processed_number[country_number[:code].length..-1]
484
+ end
485
+
486
+ # Limit returned string to 3 characters + | + 15 characters
487
+ adjust_phone_number_length(country_number[:code], processed_number)
195
488
  end
196
489
 
197
490
  def lookup_state_code(country_code, state)
@@ -213,6 +506,48 @@ module OffsitePayments #:nodoc:
213
506
  add_field("HPP_SHIPPING_#{k.split('HPP_BILLING_')[1]}", v)
214
507
  end
215
508
  end
509
+
510
+ # Validations
511
+ def get_pattern(key)
512
+ case key
513
+ when 'HPP_CUSTOMER_EMAIL' then /^([a-zA-Z0-9_\-\.]+)@([a-zA-Z0-9_\-\.]+)\.([a-zA-Z]{2,24})*$/
514
+ when 'HPP_CUSTOMER_PHONENUMBER_MOBILE' then /^([0-9 +]){1,3}(\|){0,1}([0-9 +]){1,15}$/
515
+ when 'HPP_BILLING_STREET1', 'HPP_SHIPPING_STREET1', 'HPP_BILLING_STREET2', 'HPP_SHIPPING_STREET2' then /^[ÀÁÂÃÂÄÅÆÇÈÉÊËÌÍÎÏÐÑÒÓÔÕÖרÙÚÛÜÝÞßàáâãäåªæçèéêëìíîïðñòóôõöº÷ø¤ùúûüýþÿ~L~N~Z~\~^~_¥a-zA-Z0-9.'";\s,\+\-£\/@!\?%\*:$#\[\]|=\\&amp;\u0152\u0153\u017D\u0161\u017E\u0178\u20AC]{1,50}$/
516
+ when 'HPP_BILLING_CITY', 'HPP_SHIPPING_CITY' then /^[ÀÁÂÃÂÄÅÆÇÈÉÊËÌÍÎÏÐÑÒÓÔÕÖרÙÚÛÜÝÞßàáâãäåªæçèéêëìíîïðñòóôõöº÷ø¤ùúûüýþÿ~L~N~Z~\~^~_¥a-zA-Z0-9.'";\s,\+\-£\/@!\?%\*:$#\[\]|=\\&amp;\u0152\u0153\u017D\u0161\u017E\u0178\u20AC]{1,40}$/
517
+ when 'HPP_BILLING_COUNTRY', 'HPP_SHIPPING_COUNTRY' then /^([0-9])*$/
518
+ when 'HPP_BILLING_POSTALCODE', 'HPP_SHIPPING_POSTALCODE' then /^[a-zA-Z0-9\-\s]{1,16}$/
519
+ when 'HPP_BILLING_STATE', 'HPP_SHIPPING_STATE' then /^([A-Z])*$/
520
+ end
521
+ end
522
+
523
+ def get_message(key)
524
+ case key
525
+ when 'HPP_CUSTOMER_EMAIL' then 'Invalid E-mail address.'
526
+ when 'HPP_CUSTOMER_PHONENUMBER_MOBILE' then 'Invalid Telephone. The selected payment method only allows numbers, spaces or punctuation (+, |), and no more than 19 characters.'
527
+ when 'HPP_BILLING_STREET1', 'HPP_SHIPPING_STREET1', 'HPP_BILLING_STREET2', 'HPP_SHIPPING_STREET2' then 'Invalid Street address. The selected payment method only allows letters, numbers, spaces or punctuation, and no more than 50 characters per line.'
528
+ when 'HPP_BILLING_CITY', 'HPP_SHIPPING_CITY' then 'Invalid City. The selected payment method only allows letters, numbers, spaces or punctuation, and no more than 40 characters.'
529
+ when 'HPP_BILLING_COUNTRY', 'HPP_SHIPPING_COUNTRY' then 'Invalid Country code.'
530
+ when 'HPP_BILLING_POSTALCODE', 'HPP_SHIPPING_POSTALCODE' then 'Invalid Zip/Postal Code. The selected payment method only allows letters, numbers, spaces or punctuation, and no more than 16 characters.'
531
+ when 'HPP_BILLING_STATE', 'HPP_SHIPPING_STATE' then 'Invalid State.'
532
+ end
533
+ end
534
+
535
+ def validate(key, value)
536
+ pattern = get_pattern(key)
537
+
538
+ return value unless pattern.present?
539
+
540
+ if value =~pattern
541
+ return value
542
+ else
543
+ raise ArgumentError, get_message(key)
544
+ end
545
+ end
546
+
547
+ def add_field(name, value)
548
+ return if name.blank? || value.blank?
549
+ @fields[name.to_s] = validate(name.to_s, value.to_s)
550
+ end
216
551
  end
217
552
 
218
553
  class Helper < OffsitePayments::Helper
@@ -254,32 +589,63 @@ module OffsitePayments #:nodoc:
254
589
  def billing_address(params={})
255
590
  country = params[:country]
256
591
  country_code = lookup_country_code(country, :alpha2)
592
+ avs_code = extract_avs_code(params)
593
+ params[:state] = lookup_state_code(country_code, params[:state])
594
+
257
595
  super
258
596
 
259
- add_field(mappings[:billing_address][:zip], extract_avs_code(params))
260
597
  add_field(mappings[:billing_address][:country], lookup_country_code(country))
598
+ add_field(mappings[:billing_address][:code], avs_code)
599
+
600
+ unless ['US', 'CA'].include?(country_code)
601
+ # HPP_BILLING_STATE is required only for US and CA, otherwise is deleted
602
+ @fields.delete_if do |k, _|
603
+ k == 'HPP_BILLING_STATE'
604
+ end
605
+ end
606
+
607
+ unless ['US', 'CA', 'GB'].include?(country_code)
608
+ # BILLING_CODE is required only for US, CA and GB, otherwise is nil,
609
+ # therefore the field is deleted for the other countries
610
+ @fields.delete_if do |k, _|
611
+ k == 'BILLING_CODE'
612
+ end
613
+ end
261
614
 
262
- if ['US', 'CA'].include?(country_code) && params[:state].length > 2
263
- add_field(mappings[:billing_address][:state], lookup_state_code(country_code, params[:state]))
615
+ if @fields[mappings[:customer][:phone]]
616
+ add_field(mappings[:customer][:phone], format_phone_number(@phone_number, country_code))
264
617
  end
265
618
  end
266
619
 
267
620
  def shipping_address(params={})
268
621
  country = params[:country]
269
622
  country_code = lookup_country_code(country, :alpha2)
623
+ params[:state] = lookup_state_code(country_code, params[:state])
624
+
270
625
  super
271
626
 
272
- add_field(mappings[:shipping_address][:zip], extract_avs_code(params))
273
- add_field(mappings[:shipping_address][:country], lookup_country_code(params[:country]))
627
+ add_field(mappings[:shipping_address][:country], lookup_country_code(country))
628
+ # the mapping for 'SHIPPING_CODE' field, which has the same value as the 'HPP_SHIPPING_POSTALCODE'
629
+ add_field(mappings[:shipping_address][:code], params[:zip])
630
+
631
+ unless ['US', 'CA'].include?(country_code)
632
+ # HPP_SHIPPING_STATE is required only for US and CA, otherwise is deleted
633
+ @fields.delete_if do |k, _|
634
+ k == 'HPP_SHIPPING_STATE'
635
+ end
636
+ end
274
637
 
275
- if ['US', 'CA'].include?(country_code) && params[:state].length > 2
276
- add_field(mappings[:shipping_address][:state], lookup_state_code(country_code, params[:state]))
638
+ if @fields[mappings[:customer][:phone]]&.[](0..1) == '0|'
639
+ add_field(mappings[:customer][:phone], format_phone_number(@phone_number, country_code))
277
640
  end
278
641
  end
279
642
 
280
643
  def customer(params={})
644
+ country = @fields[mappings[:billing_address][:country]]
645
+ @phone_number = params[:phone]
646
+ params[:phone] = format_phone_number(@phone_number, lookup_country_code(country, :alpha2))
647
+
281
648
  super
282
- add_field(mappings[:customer][:phone], format_phone_number(params[:phone]))
283
649
  end
284
650
 
285
651
  def addresses_match(address_match = nil)
@@ -339,7 +705,8 @@ module OffsitePayments #:nodoc:
339
705
  :address2 => 'HPP_SHIPPING_STREET2',
340
706
  :address3 => 'HPP_SHIPPING_STREET3',
341
707
  :city => 'HPP_SHIPPING_CITY',
342
- :state => 'HPP_SHIPPING_STATE'
708
+ :state => 'HPP_SHIPPING_STATE',
709
+ :code => 'SHIPPING_CODE'
343
710
 
344
711
  mapping :billing_address, :zip => 'HPP_BILLING_POSTALCODE',
345
712
  :country => 'HPP_BILLING_COUNTRY',
@@ -347,7 +714,8 @@ module OffsitePayments #:nodoc:
347
714
  :address2 => 'HPP_BILLING_STREET2',
348
715
  :address3 => 'HPP_BILLING_STREET3',
349
716
  :city => 'HPP_BILLING_CITY',
350
- :state => 'HPP_BILLING_STATE'
717
+ :state => 'HPP_BILLING_STATE',
718
+ :code => 'BILLING_CODE'
351
719
 
352
720
  mapping :addresses_match, 'HPP_ADDRESS_MATCH_INDICATOR'
353
721
  mapping :comment, 'COMMENT2'
@@ -424,10 +792,6 @@ module OffsitePayments #:nodoc:
424
792
  params['MESSAGE']
425
793
  end
426
794
 
427
- def pasref
428
- params['PASREF']
429
- end
430
-
431
795
  def authcode
432
796
  params['AUTHCODE']
433
797
  end
@@ -72,6 +72,7 @@ module OffsitePayments #:nodoc:
72
72
  attr_reader :identifier
73
73
 
74
74
  def initialize(order, account, options={})
75
+ @shipping_address_set = nil
75
76
  super
76
77
  @identifier = rand(0..99999).to_s.rjust(5, '0')
77
78
  add_field 'VendorTxCode', "#{order}-#{@identifier}"
@@ -22,7 +22,6 @@ module OffsitePayments #:nodoc:
22
22
  'CVE' => 0,
23
23
  'DJF' => 0,
24
24
  'GNF' => 0,
25
- 'HUF' => 0,
26
25
  'ISK' => 0,
27
26
  'JPY' => 0,
28
27
  'KMF' => 0,
@@ -150,7 +150,7 @@ module OffsitePayments #:nodoc:
150
150
  end
151
151
 
152
152
  def amount
153
- Money.from_amount(BigDecimal.new(gross), currency)
153
+ Money.from_amount(BigDecimal(gross), currency)
154
154
  end
155
155
 
156
156
  def item_id
@@ -83,7 +83,7 @@ module OffsitePayments #:nodoc:
83
83
  end
84
84
 
85
85
  def amount
86
- Money.from_amount(BigDecimal.new(gross), currency)
86
+ Money.from_amount(BigDecimal(gross), currency)
87
87
  end
88
88
 
89
89
  def key_present?
@@ -1,3 +1,3 @@
1
1
  module OffsitePayments
2
- VERSION = "2.7.21"
2
+ VERSION = "2.7.28"
3
3
  end
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: offsite_payments
3
3
  version: !ruby/object:Gem::Version
4
- version: 2.7.21
4
+ version: 2.7.28
5
5
  platform: ruby
6
6
  authors:
7
7
  - Tobias Luetke
8
8
  autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
- date: 2019-09-23 00:00:00.000000000 Z
11
+ date: 2021-02-11 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: activesupport
@@ -257,6 +257,7 @@ files:
257
257
  - lib/offsite_payments/integrations/platron.rb
258
258
  - lib/offsite_payments/integrations/pxpay.rb
259
259
  - lib/offsite_payments/integrations/quickpay.rb
260
+ - lib/offsite_payments/integrations/quickpay_v10.rb
260
261
  - lib/offsite_payments/integrations/rbkmoney.rb
261
262
  - lib/offsite_payments/integrations/realex_offsite.rb
262
263
  - lib/offsite_payments/integrations/robokassa.rb
@@ -275,7 +276,8 @@ files:
275
276
  homepage: https://github.com/activemerchant/offsite_payments
276
277
  licenses:
277
278
  - MIT
278
- metadata: {}
279
+ metadata:
280
+ allowed_push_host: https://rubygems.org
279
281
  post_install_message: "\n In order to use `offsite_payments` gem, you need to either
280
282
  install or add to your Gemfile\n one of the two options for Money gem:\n -
281
283
  `gem 'money'`\n - `gem 'shopify-money', require: 'money'`\n\n Regardless