eway_rapid 1.0.0

Sign up to get free protection for your applications and to get access to all the features.
Files changed (76) hide show
  1. checksums.yaml +7 -0
  2. data/.gitignore +25 -0
  3. data/.travis.yml +11 -0
  4. data/CHANGELOG.md +7 -0
  5. data/Gemfile +2 -0
  6. data/LICENSE.md +21 -0
  7. data/README.md +96 -0
  8. data/Rakefile +14 -0
  9. data/eway_rapid.gemspec +26 -0
  10. data/lib/eway_rapid.rb +78 -0
  11. data/lib/eway_rapid/constants.rb +126 -0
  12. data/lib/eway_rapid/entities/cancel_authorisation_request.rb +9 -0
  13. data/lib/eway_rapid/entities/cancel_authorisation_response.rb +34 -0
  14. data/lib/eway_rapid/entities/capture_payment_request.rb +11 -0
  15. data/lib/eway_rapid/entities/capture_payment_response.rb +34 -0
  16. data/lib/eway_rapid/entities/create_access_code_request.rb +35 -0
  17. data/lib/eway_rapid/entities/create_access_code_response.rb +128 -0
  18. data/lib/eway_rapid/entities/create_access_code_shared_request.rb +53 -0
  19. data/lib/eway_rapid/entities/create_access_code_shared_response.rb +40 -0
  20. data/lib/eway_rapid/entities/create_customer_response.rb +8 -0
  21. data/lib/eway_rapid/entities/direct_customer_search_request.rb +9 -0
  22. data/lib/eway_rapid/entities/direct_customer_search_response.rb +23 -0
  23. data/lib/eway_rapid/entities/direct_payment_request.rb +29 -0
  24. data/lib/eway_rapid/entities/direct_payment_response.rb +58 -0
  25. data/lib/eway_rapid/entities/direct_refund_request.rb +26 -0
  26. data/lib/eway_rapid/entities/direct_refund_response.rb +44 -0
  27. data/lib/eway_rapid/entities/transaction_search_response.rb +23 -0
  28. data/lib/eway_rapid/exceptions.rb +51 -0
  29. data/lib/eway_rapid/message/convert/customer_to_internal_customer.rb +70 -0
  30. data/lib/eway_rapid/message/convert/direct_payment_to_trans_status.rb +47 -0
  31. data/lib/eway_rapid/message/convert/direct_refund_to_trans_status.rb +33 -0
  32. data/lib/eway_rapid/message/convert/internal_customer_to_customer.rb +41 -0
  33. data/lib/eway_rapid/message/convert/internal_trans_to_trans.rb +62 -0
  34. data/lib/eway_rapid/message/convert/internal_transaction_to_address.rb +27 -0
  35. data/lib/eway_rapid/message/convert/internal_transaction_to_status.rb +55 -0
  36. data/lib/eway_rapid/message/convert/payment_to_payment_details.rb +25 -0
  37. data/lib/eway_rapid/message/convert/request/refund_to_direct_refund_req.rb +41 -0
  38. data/lib/eway_rapid/message/convert/request/transaction_to_capture_payment.rb +28 -0
  39. data/lib/eway_rapid/message/convert/request/transaction_to_create_access_code_request.rb +58 -0
  40. data/lib/eway_rapid/message/convert/request/transaction_to_create_access_code_shared_request.rb +54 -0
  41. data/lib/eway_rapid/message/convert/request/transaction_to_direct_payment.rb +45 -0
  42. data/lib/eway_rapid/message/convert/response/access_code_shared_to_create_cust.rb +23 -0
  43. data/lib/eway_rapid/message/convert/response/access_code_shared_to_create_trans.rb +28 -0
  44. data/lib/eway_rapid/message/convert/response/access_code_to_create_cust.rb +24 -0
  45. data/lib/eway_rapid/message/convert/response/access_code_to_create_trans.rb +27 -0
  46. data/lib/eway_rapid/message/convert/response/cancel_authorisation_to_refund.rb +37 -0
  47. data/lib/eway_rapid/message/convert/response/capture_payment_to_create_transaction.rb +43 -0
  48. data/lib/eway_rapid/message/convert/response/direct_customer_to_query_customer.rb +55 -0
  49. data/lib/eway_rapid/message/convert/response/direct_payment_to_create_cust.rb +23 -0
  50. data/lib/eway_rapid/message/convert/response/direct_payment_to_create_trans.rb +32 -0
  51. data/lib/eway_rapid/message/convert/response/direct_refund_to_refund_response.rb +28 -0
  52. data/lib/eway_rapid/message/convert/response/search_to_query_trans.rb +30 -0
  53. data/lib/eway_rapid/message/convert/shipping_details_to_address.rb +35 -0
  54. data/lib/eway_rapid/message/convert/transaction_shipping_address.rb +37 -0
  55. data/lib/eway_rapid/message/convert/transaction_to_arr_line_item.rb +14 -0
  56. data/lib/eway_rapid/message/convert/transaction_to_arr_option.rb +25 -0
  57. data/lib/eway_rapid/message/convert/transaction_to_payment.rb +29 -0
  58. data/lib/eway_rapid/message/convert/verification_to_verification_result.rb +33 -0
  59. data/lib/eway_rapid/message/process/customer_process.rb +255 -0
  60. data/lib/eway_rapid/message/process/refund_process.rb +76 -0
  61. data/lib/eway_rapid/message/process/rest_process.rb +87 -0
  62. data/lib/eway_rapid/message/process/transaction_process.rb +139 -0
  63. data/lib/eway_rapid/models/enums.rb +126 -0
  64. data/lib/eway_rapid/models/internal_models.rb +431 -0
  65. data/lib/eway_rapid/models/models.rb +334 -0
  66. data/lib/eway_rapid/output/create_transaction_response.rb +24 -0
  67. data/lib/eway_rapid/output/query_customer_response.rb +25 -0
  68. data/lib/eway_rapid/output/query_transaction_response.rb +16 -0
  69. data/lib/eway_rapid/output/refund_response.rb +9 -0
  70. data/lib/eway_rapid/output/response_output.rb +14 -0
  71. data/lib/eway_rapid/rapid_client.rb +444 -0
  72. data/lib/eway_rapid/rapid_logger.rb +40 -0
  73. data/lib/eway_rapid/resources/err_code_resource_en.yml +237 -0
  74. data/lib/eway_rapid/resources/rapid-api.yml +4 -0
  75. data/lib/eway_rapid/version.rb +3 -0
  76. metadata +201 -0
@@ -0,0 +1,334 @@
1
+ module EwayRapid
2
+ module Models
3
+
4
+ # Customer's address
5
+ class Address
6
+
7
+ # First line of the street address
8
+ attr_accessor :street1
9
+
10
+ # Second line of the street address
11
+ attr_accessor :street2
12
+
13
+ attr_accessor :city
14
+ attr_accessor :state
15
+
16
+ # Two letter ISO 3166-1 alpha-2 code
17
+ attr_accessor :country
18
+
19
+ attr_accessor :postal_code
20
+ end
21
+
22
+ # Card information
23
+ class CardDetails
24
+ attr_accessor :name
25
+ attr_accessor :number
26
+ attr_accessor :expiry_month
27
+ attr_accessor :expiry_year
28
+ attr_accessor :start_month
29
+ attr_accessor :start_year
30
+ attr_accessor :issue_number
31
+ attr_accessor :cvn
32
+
33
+ def self.to_hash(card_details)
34
+ { Constants::NAME => card_details.name,
35
+ Constants::NUMBER => card_details.number,
36
+ Constants::EXPIRY_MONTH => card_details.expiry_month,
37
+ Constants::EXPIRY_YEAR => card_details.expiry_year,
38
+ Constants::START_MONTH => card_details.start_month,
39
+ Constants::START_YEAR => card_details.start_year,
40
+ Constants::ISSUE_NUMBER => card_details.issue_number,
41
+ Constants::CVN => card_details.cvn } if card_details
42
+ end
43
+
44
+ def self.from_json(json)
45
+ hash = JSON.parse(json)
46
+ from_hash(hash)
47
+ end
48
+
49
+ def self.from_hash(hash)
50
+ unless hash.nil?
51
+ card_details = CardDetails.new
52
+ card_details.name = hash[Constants::NAME]
53
+ card_details.number = hash[Constants::NUMBER]
54
+ card_details.expiry_month = hash[Constants::EXPIRY_MONTH]
55
+ card_details.expiry_year = hash[Constants::EXPIRY_YEAR]
56
+ card_details.start_month = hash[Constants::START_MONTH]
57
+ card_details.start_year = hash[Constants::START_YEAR]
58
+ card_details.issue_number = hash[Constants::ISSUE_NUMBER]
59
+ card_details.cvn = hash[Constants::CVN]
60
+ card_details
61
+ end
62
+ end
63
+ end
64
+
65
+ # Customer details
66
+ class Customer
67
+ attr_accessor :token_customer_id
68
+ attr_accessor :reference
69
+ attr_accessor :title
70
+ attr_accessor :first_name
71
+ attr_accessor :last_name
72
+ attr_accessor :company_name
73
+ attr_accessor :job_description
74
+ attr_accessor :address
75
+ attr_accessor :phone
76
+ attr_accessor :mobile
77
+ attr_accessor :email
78
+ attr_accessor :fax
79
+ attr_accessor :url
80
+ attr_accessor :comments
81
+ attr_accessor :card_details
82
+ attr_accessor :redirect_url
83
+ attr_accessor :cancel_url
84
+ attr_accessor :customer_device_ip
85
+ end
86
+
87
+ # Item information
88
+ class LineItem
89
+
90
+ # The stock keeping unit used to identify this line item
91
+ attr_accessor :sku
92
+ attr_accessor :description
93
+ attr_accessor :quantity
94
+
95
+ # The unit cost of this line item in cents
96
+ attr_accessor :unit_cost
97
+
98
+ # The tax amount that applies to this line item in cents
99
+ attr_accessor :tax
100
+
101
+ # The total amount (including tax) charged for this line item in the cents
102
+ attr_accessor :total
103
+
104
+ # Set the line item's values so that the total and tax add up
105
+ # correctly
106
+ #
107
+ # @param [Integer] unit_cost
108
+ # @param [Integer] unit_tax
109
+ # @param [Integer] quantity
110
+ def calculate(unit_cost, unit_tax, quantity)
111
+ if unit_cost && unit_tax && quantity
112
+ tax = unit_tax * quantity
113
+ quantity * unit_cost + tax
114
+ end
115
+ end
116
+
117
+ def self.to_hash(line_item)
118
+ { Constants::SKU => line_item.sku,
119
+ Constants::DESCRIPTION => line_item.description,
120
+ Constants::QUANTITY => line_item.quantity,
121
+ Constants::UNIT_COST => line_item.unit_cost,
122
+ Constants::TAX => line_item.tax,
123
+ Constants::TOTAL => line_item.total } if line_item
124
+ end
125
+
126
+ def self.to_array(array)
127
+ line_items = []
128
+ if array
129
+ array.each {|line_item_hash|
130
+ obj = to_hash(line_item_hash)
131
+ line_items.push(obj)
132
+ }
133
+ end
134
+ line_items
135
+ end
136
+
137
+ def self.from_json(json)
138
+ hash = JSON.parse(json)
139
+ from_hash(hash)
140
+ end
141
+
142
+ def self.from_hash(hash)
143
+ line_item = LineItem.new
144
+ line_item.sku = hash[Constants::SKU]
145
+ line_item.description = hash[Constants::DESCRIPTION]
146
+ line_item.quantity = hash[Constants::QUANTITY]
147
+ line_item.unit_cost = hash[Constants::UNIT_COST]
148
+ line_item.tax = hash[Constants::TAX]
149
+ line_item.total = hash[Constants::TOTAL]
150
+ line_item
151
+ end
152
+
153
+ def self.from_array(array)
154
+ line_items = Array.new
155
+ array.each {|line_item_hash|
156
+ obj = from_hash(line_item_hash)
157
+ line_items.push(obj)
158
+ }
159
+ line_items
160
+ end
161
+ end
162
+
163
+ # Details of the payment
164
+ class PaymentDetails
165
+
166
+ # The total amount of the transaction in cents
167
+ attr_accessor :total_amount
168
+
169
+ attr_accessor :invoice_number
170
+ attr_accessor :invoice_description
171
+ attr_accessor :invoice_reference
172
+
173
+ # The ISO 4217 3 character code of the currency that the transaction is
174
+ # to be processed in (e.g. 'AUD')
175
+ attr_accessor :currency_code
176
+ end
177
+
178
+ # Combines together all the bank/gateway specific status information for a
179
+ # transaction
180
+ class ProcessingDetails
181
+
182
+ # The bank's authorization code for the transaction
183
+ attr_accessor :authorisation_code
184
+
185
+ # The bank's Response code
186
+ attr_accessor :response_code
187
+
188
+ # The bank or gateway's Response message
189
+ attr_accessor :response_message
190
+ end
191
+
192
+ # Contains the high level properties required to process a refund
193
+ # (or Authorisation Cancel)
194
+ class Refund
195
+ attr_accessor :customer
196
+ attr_accessor :shipping_details
197
+ attr_accessor :refund_details
198
+ attr_accessor :line_items
199
+ attr_accessor :options
200
+ attr_accessor :device_id
201
+ attr_accessor :partner_id
202
+ end
203
+
204
+ # Contains the Shipping related information for a transaction
205
+ class ShippingDetails
206
+ attr_accessor :first_name
207
+ attr_accessor :last_name
208
+ attr_accessor :shipping_method
209
+ attr_accessor :shipping_address
210
+ attr_accessor :email
211
+ attr_accessor :phone
212
+ attr_accessor :fax
213
+ end
214
+
215
+ # The details of a transaction that will be processed either via the responsive
216
+ # shared page, by transparent redirect, by Direct, or one that is captured from
217
+ # a previous Authorisation transaction
218
+ class Transaction
219
+
220
+ # The type of transaction being performed - use Enums::TransactionType
221
+ attr_accessor :transaction_type
222
+
223
+ # Set to true to capture funds immediately, false to authorise only
224
+ attr_accessor :capture
225
+
226
+ # Customer details for the transaction
227
+ attr_accessor :customer
228
+
229
+ # Shipping details fo the transaction
230
+ attr_accessor :shipping_details
231
+
232
+ # Payment details for the transaction
233
+ attr_accessor :payment_details
234
+
235
+ # Array of line items for the transaction
236
+ attr_accessor :line_items
237
+
238
+ # Array of options to pass to eWAY
239
+ attr_accessor :options
240
+
241
+ # The identification name/number for the device or application processing the transaction
242
+ attr_accessor :device_id
243
+
244
+ # The partner ID generated from an eWAY partner agreement
245
+ attr_accessor :partner_id
246
+
247
+ # The wallet ID of a third party wallet used for a payment
248
+ attr_accessor :third_party_wallet_id
249
+
250
+ # The Transaction ID of an authorisation to capture
251
+ attr_accessor :auth_transaction_id
252
+
253
+ # The URL that the shared page redirects to after a payment is processed
254
+ # (transparent redirect & responsive shared page only)
255
+ attr_accessor :redirect_url
256
+
257
+ # The URL that the shared page redirects to if a customer cancels the transaction
258
+ # (responsive shared page only)
259
+ attr_accessor :cancel_url
260
+
261
+ # Setting this to +true+ will process a PayPal Checkout payment.
262
+ attr_accessor :checkout_payment
263
+
264
+ # The URL that the customer is to be returned to after logging in to their PayPal account.
265
+ # (transparent redirect & responsive shared page with PayPal Checkout only)
266
+ attr_accessor :checkout_url
267
+
268
+ # Set the theme of the Responsive Shared Page from 12 available themes
269
+ attr_accessor :custom_view
270
+
271
+ # Short text description to be placed under the logo on the Responsive Shared Page
272
+ attr_accessor :header_text
273
+
274
+ # Language code determines the language that the shared page will be displayed in.
275
+ # One of: EN (English, default), ES (Spanish)
276
+ attr_accessor :language
277
+
278
+ # When set to false, cardholders will be able to edit the information on the Responsive Shared Page
279
+ attr_accessor :customer_read_only
280
+
281
+ # Set whether the customer's phone number should be confirmed using Beagle Verify
282
+ attr_accessor :verify_customer_phone
283
+
284
+ # Set whether the customer's email should be confirmed using Beagle Verify
285
+ attr_accessor :verify_customer_email
286
+
287
+ # The URL of the merchant's logo to display on the Responsive Shared Page
288
+ attr_accessor :logo_url
289
+
290
+ alias_method :customer_read_only?, :customer_read_only
291
+ alias_method :checkout_payment?, :checkout_payment
292
+ alias_method :verify_customer_phone?, :verify_customer_phone
293
+ alias_method :verify_customer_email?, :verify_customer_email
294
+
295
+ def initialize
296
+ @capture = true
297
+ end
298
+ end
299
+
300
+ # Contains the status information for a transaction
301
+ class TransactionStatus
302
+ attr_accessor :transaction_id
303
+ attr_accessor :total
304
+ attr_accessor :status
305
+ attr_accessor :captured
306
+ attr_accessor :beagle_score
307
+ attr_accessor :fraud_action
308
+ attr_accessor :verification_result
309
+ attr_accessor :processing_details
310
+
311
+ alias_method :status?, :status
312
+ end
313
+
314
+ # Contains the result of all the Beagle and Payment provider verification
315
+ class VerificationResult
316
+ # Currently unused
317
+ attr_accessor :cvn
318
+ # Currently unused
319
+ attr_accessor :address
320
+ # Currently unused
321
+ attr_accessor :email
322
+ # Currently unused
323
+ attr_accessor :mobile
324
+ # Currently unused
325
+ attr_accessor :phone
326
+
327
+ # The result of the Beagle Verify email verification
328
+ attr_accessor :beagle_email
329
+
330
+ # The result of the Beagle Verify phone verification
331
+ attr_accessor :beagle_phone
332
+ end
333
+ end
334
+ end
@@ -0,0 +1,24 @@
1
+ module EwayRapid
2
+ # Create transaction response
3
+ class CreateTransactionResponse < ResponseOutput
4
+
5
+ # The transaction as returned by Rapid API.
6
+ attr_accessor :transaction
7
+
8
+ # Contains transaction status information
9
+ attr_accessor :transaction_status
10
+
11
+ # URL to the Responsive Shared Page that the cardholder's browser should
12
+ # be redirected to (Only for Responsive Shared)
13
+ attr_accessor :shared_payment_url
14
+
15
+ # URL that the merchant's credit card form should post to to complete
16
+ # payment (Only for Transparent Redirect)
17
+ attr_accessor :form_action_url
18
+
19
+ # An AccessCode for this transaction (Used with Transparent Redirect
20
+ # and Responsive Shared)
21
+ attr_accessor :access_code
22
+
23
+ end
24
+ end
@@ -0,0 +1,25 @@
1
+ module EwayRapid
2
+ # Query customer response data
3
+ class QueryCustomerResponse < ResponseOutput
4
+ attr_accessor :token_customer_id
5
+ attr_accessor :state
6
+ attr_accessor :postal_code
7
+ attr_accessor :email
8
+ attr_accessor :reference
9
+ attr_accessor :title
10
+ attr_accessor :first_name
11
+ attr_accessor :last_name
12
+ attr_accessor :company_name
13
+ attr_accessor :job_description
14
+ attr_accessor :street1
15
+ attr_accessor :street2
16
+ attr_accessor :city
17
+ attr_accessor :phone
18
+ attr_accessor :mobile
19
+ attr_accessor :url
20
+ attr_accessor :card_detail
21
+ attr_accessor :country
22
+ attr_accessor :comments
23
+ attr_accessor :fax
24
+ end
25
+ end
@@ -0,0 +1,16 @@
1
+ module EwayRapid
2
+ # Query transaction response
3
+ class QueryTransactionResponse < ResponseOutput
4
+
5
+ # The Request as returned by Rapid API. Where a token customer is created as
6
+ # result of the transaction, then the Customer in this type will contain the
7
+ # Customer Token ID
8
+ attr_accessor :transaction
9
+
10
+ # Contains transaction status information
11
+ attr_accessor :transaction_status
12
+
13
+ # AccessCode for this transaction
14
+ attr_accessor :access_code
15
+ end
16
+ end
@@ -0,0 +1,9 @@
1
+ module EwayRapid
2
+ # Refund response
3
+ class RefundResponse < ResponseOutput
4
+ attr_accessor :refund
5
+
6
+ # Contains transaction status information
7
+ attr_accessor :transaction_status
8
+ end
9
+ end
@@ -0,0 +1,14 @@
1
+ module EwayRapid
2
+ # Base class for the output data class inherits
3
+ class ResponseOutput
4
+
5
+ # List of all validation, processing, fraud or system errors that occurred
6
+ # when processing this request.
7
+ attr_accessor :errors
8
+
9
+ def initialize(*args, &block)
10
+ super
11
+ @errors = []
12
+ end
13
+ end
14
+ end
@@ -0,0 +1,444 @@
1
+ module EwayRapid
2
+
3
+ # This class abstracts the Rapid API 3.1 functions so that it can be consumed
4
+ # by Ruby applications
5
+ #
6
+ # @author eWAY
7
+ class RapidClient
8
+
9
+ # @param [String] api_key eWAY Rapid API key
10
+ # @param [String] password eWAY Rapid API password
11
+ # @param [String] rapid_endpoint eWAY Rapid endpoint - either Sandbox or Production
12
+ def initialize(api_key, password, rapid_endpoint)
13
+ @logger = RapidLogger.logger
14
+ @logger.info "Initiate client with end point: #{rapid_endpoint}" if @logger
15
+
16
+ @api_key = api_key
17
+ @password = password
18
+ @rapid_endpoint = rapid_endpoint
19
+
20
+ validate_api_param
21
+ end
22
+
23
+ # Changes the API Key and Password the Client is configured to use
24
+ #
25
+ # @param [String] api_key eWAY Rapid API key
26
+ # @param [String] password eWAY Rapid API password
27
+ def set_credentials(api_key, password)
28
+ @api_key = api_key
29
+ @password = password
30
+
31
+ validate_api_param
32
+ end
33
+
34
+ # Creates a transaction either using an authorisation, the responsive shared
35
+ # page, transparent redirect, or direct as the source of funds
36
+ #
37
+ # @param [Enums::PaymentMethod] payment_method Describes where the card details will be coming from for this transaction (Direct, Responsive Shared, Transparent Redirect etc)
38
+ # @param [Models::Transaction] transaction Request containing the transaction details
39
+ # @return [CreateTransactionResponse] CreateTransactionResponse
40
+ def create_transaction(payment_method, transaction)
41
+ unless get_valid?
42
+ return make_response_with_exception(Exceptions::APIKeyInvalidException.new('API key, password or Rapid endpoint missing or invalid'), CreateTransactionResponse)
43
+ end
44
+ begin
45
+ case payment_method
46
+ when Enums::PaymentMethod::DIRECT
47
+ url = @rapid_endpoint + Constants::DIRECT_PAYMENT_METHOD_NAME + Constants::JSON_SUFFIX
48
+
49
+ request = Message::TransactionProcess::TransDirectPaymentMsgProcess.create_request(transaction)
50
+ response = Message::TransactionProcess::TransDirectPaymentMsgProcess.send_request(url, @api_key, @password, request)
51
+ Message::TransactionProcess::TransDirectPaymentMsgProcess.make_result(response)
52
+ when Enums::PaymentMethod::RESPONSIVE_SHARED
53
+ url = @rapid_endpoint + Constants::RESPONSIVE_SHARED_METHOD_NAME + Constants::JSON_SUFFIX
54
+
55
+ request = Message::TransactionProcess::TransResponsiveSharedMsgProcess.create_request(transaction)
56
+ response = Message::TransactionProcess::TransResponsiveSharedMsgProcess.send_request(url, @api_key, @password, request)
57
+ Message::TransactionProcess::TransResponsiveSharedMsgProcess.make_result(response)
58
+ when Enums::PaymentMethod::TRANSPARENT_REDIRECT
59
+ url = @rapid_endpoint + Constants::TRANSPARENT_REDIRECT_METHOD_NAME + Constants::JSON_SUFFIX
60
+
61
+ request = Message::TransactionProcess::TransTransparentRedirectMsgProcess.create_request(transaction)
62
+ response = Message::TransactionProcess::TransTransparentRedirectMsgProcess.send_request(url, @api_key, @password, request)
63
+ Message::TransactionProcess::TransTransparentRedirectMsgProcess.make_result(response)
64
+ when Enums::PaymentMethod::WALLET
65
+ if transaction.capture
66
+ url = @rapid_endpoint + Constants::DIRECT_PAYMENT_METHOD_NAME + Constants::JSON_SUFFIX
67
+
68
+ request = Message::TransactionProcess::TransDirectPaymentMsgProcess.create_request(transaction)
69
+ response = Message::TransactionProcess::TransDirectPaymentMsgProcess.send_request(url, @api_key, @password, request)
70
+ Message::TransactionProcess::TransDirectPaymentMsgProcess.make_result(response)
71
+ else
72
+ url = @rapid_endpoint + Constants::CAPTURE_PAYMENT_METHOD
73
+
74
+ request = Message::TransactionProcess::CapturePaymentMsgProcess.create_request(transaction)
75
+ response = Message::TransactionProcess::CapturePaymentMsgProcess.send_request(url, @api_key, @password, request)
76
+ Message::TransactionProcess::CapturePaymentMsgProcess.make_result(response)
77
+ end
78
+ when Enums::PaymentMethod::AUTHORISATION
79
+ url = @rapid_endpoint + Constants::CAPTURE_PAYMENT_METHOD
80
+
81
+ request = Message::TransactionProcess::CapturePaymentMsgProcess.create_request(transaction)
82
+ response = Message::TransactionProcess::CapturePaymentMsgProcess.send_request(url, @api_key, @password, request)
83
+ Message::TransactionProcess::CapturePaymentMsgProcess.make_result(response)
84
+ else
85
+ make_response_with_exception(Exceptions::ParameterInvalidException.new('Unsupported payment type'), CreateTransactionResponse)
86
+ end
87
+ rescue => e
88
+ @logger.error(e.to_s) if @logger
89
+ make_response_with_exception(e, CreateTransactionResponse)
90
+ end
91
+ end
92
+
93
+ # Gets transaction details given an eWAY Transaction ID
94
+ #
95
+ # @param [Integer] transaction_id eWAY Transaction ID
96
+ # @return [QueryTransactionResponse]
97
+ def query_transaction_by_id(transaction_id)
98
+ query_transaction_by_access_code(transaction_id.to_s)
99
+ end
100
+
101
+ # Gets transaction details given an access code
102
+ #
103
+ # @param [String] access_code Access code for the transaction to query
104
+ # @return [QueryTransactionResponse]
105
+ def query_transaction_by_access_code(access_code)
106
+ query_transaction_with_path(access_code, Constants::TRANSACTION_METHOD)
107
+ end
108
+
109
+ # Query a transaction by one of four properties transaction id, access
110
+ # code, invoice number, invoice reference
111
+ #
112
+ # @param [Enums::TransactionFilter] filter Filter definition for searching
113
+ def query_transaction_by_filter(filter)
114
+ index_of_value = filter.calculate_index_of_value
115
+ if index_of_value.nil?
116
+ return make_response_with_exception(Exceptions::APIKeyInvalidException.new('Invalid transaction filter'), QueryTransactionResponse)
117
+ end
118
+
119
+ case index_of_value
120
+ when Enums::TransactionFilter::TRANSACTION_ID_INDEX
121
+ query_transaction_by_id(filter.transaction_id.to_s)
122
+ when Enums::TransactionFilter::ACCESS_CODE_INDEX
123
+ query_transaction_by_access_code(filter.access_code)
124
+ when Enums::TransactionFilter::INVOICE_NUMBER_INDEX
125
+ query_transaction_with_path(filter.invoice_number, Constants::TRANSACTION_METHOD + '/' + Constants::TRANSACTION_QUERY_WITH_INVOICE_NUM_METHOD)
126
+ when Enums::TransactionFilter::INVOICE_REFERENCE_INDEX
127
+ query_transaction_with_path(filter.invoice_reference, Constants::TRANSACTION_METHOD + '/' + Constants::TRANSACTION_QUERY_WITH_INVOICE_REF_METHOD)
128
+ else
129
+ make_response_with_exception(Exceptions::APIKeyInvalidException.new('Invalid transaction filter'), QueryTransactionResponse)
130
+ end
131
+ end
132
+
133
+ # Refunds all or part of a transaction
134
+ #
135
+ # @param [Models::Refund] refund contains information to refund
136
+ # @return [RefundResponse]
137
+ def refund(refund)
138
+ unless @is_valid
139
+ return make_response_with_exception(Exceptions::APIKeyInvalidException.new('API key, password or Rapid endpoint missing or invalid'), RefundResponse)
140
+ end
141
+
142
+ begin
143
+ url = @rapid_endpoint + Constants::TRANSACTION_METHOD
144
+
145
+ request = Message::RefundProcess::RefundMsgProcess.create_request(refund)
146
+ response = Message::RefundProcess::RefundMsgProcess.send_request(url, @api_key, @password, request)
147
+ Message::RefundProcess::RefundMsgProcess.make_result(response)
148
+ rescue => e
149
+ @logger.error(e.to_s) if @logger
150
+ make_response_with_exception(e, RefundResponse)
151
+ end
152
+ end
153
+
154
+ # Cancel a non-captured transaction (an authorisation)
155
+ #
156
+ # @param [Models::Refund] refund contains transaction to cancel
157
+ # @return [RefundResponse]
158
+ def cancel(refund)
159
+ unless @is_valid
160
+ return make_response_with_exception(Exceptions::APIKeyInvalidException.new('API key, password or Rapid endpoint missing or invalid'), RefundResponse)
161
+ end
162
+ begin
163
+ url = @rapid_endpoint + Constants::CANCEL_AUTHORISATION_METHOD
164
+
165
+ request = Message::RefundProcess::CancelAuthorisationMsgProcess.create_request(refund)
166
+ response = Message::RefundProcess::CancelAuthorisationMsgProcess.send_request(url, @api_key, @password, request)
167
+ Message::RefundProcess::CancelAuthorisationMsgProcess.make_result(response)
168
+ rescue => e
169
+ @logger.error(e.to_s) if @logger
170
+ make_response_with_exception(e, RefundResponse)
171
+ end
172
+ end
173
+
174
+ # Creates a token customer to store card details in the secure eWAY Vault
175
+ # for charging later
176
+ #
177
+ # @param [Enums::PaymentMethod] payment_method Describes where the card details will be coming from for this transaction (Direct, Responsive Shared, Transparent Redirect etc).
178
+ # @param [Models::Customer] customer The customer's details
179
+ # @return [CreateCustomerResponse]
180
+ def create_customer(payment_method, customer)
181
+ unless get_valid?
182
+ return make_response_with_exception(Exceptions::APIKeyInvalidException.new('API key, password or Rapid endpoint missing or invalid'), CreateCustomerResponse)
183
+ end
184
+ begin
185
+ case payment_method
186
+ when Enums::PaymentMethod::DIRECT
187
+ url = @rapid_endpoint + Constants::DIRECT_PAYMENT_METHOD_NAME + Constants::JSON_SUFFIX
188
+
189
+ request = Message::CustomerProcess::CustDirectPaymentMsgProcess.create_request(customer)
190
+ response = Message::CustomerProcess::CustDirectPaymentMsgProcess.send_request(url, @api_key, @password, request)
191
+ Message::CustomerProcess::CustDirectPaymentMsgProcess.make_result(response)
192
+ when Enums::PaymentMethod::RESPONSIVE_SHARED
193
+ url = @rapid_endpoint + Constants::RESPONSIVE_SHARED_METHOD_NAME + Constants::JSON_SUFFIX
194
+
195
+ request = Message::CustomerProcess::CustResponsiveSharedMsgProcess.create_request(customer)
196
+ response = Message::CustomerProcess::CustResponsiveSharedMsgProcess.send_request(url, @api_key, @password, request)
197
+ Message::CustomerProcess::CustResponsiveSharedMsgProcess.make_result(response)
198
+ when Enums::PaymentMethod::TRANSPARENT_REDIRECT
199
+ url = @rapid_endpoint + Constants::TRANSPARENT_REDIRECT_METHOD_NAME + Constants::JSON_SUFFIX
200
+
201
+ request = Message::CustomerProcess::CustTransparentRedirectMsgProcess.create_request(customer)
202
+ response = Message::CustomerProcess::CustTransparentRedirectMsgProcess.send_request(url, @api_key, @password, request)
203
+ Message::CustomerProcess::CustTransparentRedirectMsgProcess.make_result(response)
204
+ else
205
+ make_response_with_exception(Exceptions::ParameterInvalidException.new('Unsupported payment type'), CreateCustomerResponse)
206
+ end
207
+ rescue => e
208
+ @logger.error(e.to_s) if @logger
209
+ make_response_with_exception(e, CreateCustomerResponse)
210
+ end
211
+ end
212
+
213
+ # Updates an existing token customer for the merchant in their eWAY account.
214
+ #
215
+ # @param [Enums::PaymentMethod] payment_method Describes where the card details will be coming from for this transaction (Direct, Responsive Shared, Transparent Redirect etc).
216
+ # @param [Models::Customer] customer The customer's details
217
+ # @return [CreateCustomerResponse]
218
+ def update_customer(payment_method, customer)
219
+ unless get_valid?
220
+ return make_response_with_exception(Exceptions::APIKeyInvalidException.new('API key, password or Rapid endpoint missing or invalid'), CreateCustomerResponse)
221
+ end
222
+ begin
223
+ case payment_method
224
+ when Enums::PaymentMethod::DIRECT
225
+ url = @rapid_endpoint + Constants::DIRECT_PAYMENT_METHOD_NAME + Constants::JSON_SUFFIX
226
+ request = Message::CustomerProcess::CustDirectUpdateMsgProcess.create_request(customer)
227
+ response = Message::CustomerProcess::CustDirectUpdateMsgProcess.send_request(url, @api_key, @password, request)
228
+ Message::CustomerProcess::CustDirectUpdateMsgProcess.make_result(response)
229
+ when Enums::PaymentMethod::RESPONSIVE_SHARED
230
+ url = @rapid_endpoint + Constants::RESPONSIVE_SHARED_METHOD_NAME + Constants::JSON_SUFFIX
231
+
232
+ request = Message::CustomerProcess::CustResponsiveUpdateMsgProcess.create_request(customer)
233
+ response = Message::CustomerProcess::CustResponsiveUpdateMsgProcess.send_request(url, @api_key, @password, request)
234
+ Message::CustomerProcess::CustResponsiveUpdateMsgProcess.make_result(response)
235
+ when Enums::PaymentMethod::TRANSPARENT_REDIRECT
236
+ url = @rapid_endpoint + Constants::TRANSPARENT_REDIRECT_METHOD_NAME + Constants::JSON_SUFFIX
237
+
238
+ request = Message::CustomerProcess::CustTransparentUpdateMsgProcess.create_request(customer)
239
+ response = Message::CustomerProcess::CustTransparentUpdateMsgProcess.send_request(url, @api_key, @password, request)
240
+ Message::CustomerProcess::CustTransparentUpdateMsgProcess.make_result(response)
241
+ else
242
+ return make_response_with_exception(Exceptions::ParameterInvalidException.new('Unsupported payment type'), CreateCustomerResponse)
243
+ end
244
+ rescue => e
245
+ @logger.error(e.to_s) if @logger
246
+ make_response_with_exception(e, CreateCustomerResponse)
247
+ end
248
+ end
249
+
250
+ # Returns the details of a Token Customer. This includes the masked card information
251
+ # for displaying in a UI
252
+ #
253
+ # @param [Integer] token_customer_id eWAY Token Customer ID to look up.
254
+ # @return [QueryCustomerResponse]
255
+ def query_customer(token_customer_id)
256
+ @logger.debug('Query customer with id:' + token_customer_id.to_s) if @logger
257
+ unless @is_valid
258
+ return make_response_with_exception(Exceptions::APIKeyInvalidException.new('API key, password or Rapid endpoint missing or invalid'), QueryCustomerResponse)
259
+ end
260
+ begin
261
+ url = @rapid_endpoint + Constants::DIRECT_CUSTOMER_SEARCH_METHOD + Constants::JSON_SUFFIX
262
+ url = URI.encode(url)
263
+
264
+ request = Message::CustomerProcess::QueryCustomerMsgProcess.create_request(token_customer_id.to_s)
265
+ response = Message::CustomerProcess::QueryCustomerMsgProcess.send_request(url, @api_key, @password, request)
266
+ Message::CustomerProcess::QueryCustomerMsgProcess.make_result(response)
267
+ rescue => e
268
+ @logger.error(e.to_s) if @logger
269
+ make_response_with_exception(e, QueryCustomerResponse)
270
+ end
271
+ end
272
+
273
+ # Translate an error code to a user friendly message
274
+ #
275
+ # @param [String] code The code to translate
276
+ # @param [String] language The 2 letter code for the language to translate to (only en at this time)
277
+ # @return [String] Error message
278
+ def self.user_display_message(code, language = 'en')
279
+ find_error_code(code, language)
280
+ end
281
+
282
+ # Gets the valid status of this Rapid client
283
+ #
284
+ # @return Rapid Client status
285
+ def get_valid?
286
+ @is_valid
287
+ end
288
+
289
+ # Returns all errors related to the query request of this client
290
+ #
291
+ # @return List of error codes
292
+ def get_errors
293
+ @list_error || []
294
+ end
295
+
296
+ private
297
+
298
+ # Perform a transaction query with the given path
299
+ #
300
+ # @param [String] request the transaction identifier to query
301
+ # @param [String] request_path the path to use for the query
302
+ # @return [QueryTransactionResponse]
303
+ def query_transaction_with_path(request, request_path)
304
+ unless @is_valid
305
+ return make_response_with_exception(Exceptions::APIKeyInvalidException.new('API key, password or Rapid endpoint missing or invalid'), QueryTransactionResponse)
306
+ end
307
+ begin
308
+ if request.nil? || request == ''
309
+ url = @rapid_endpoint + request_path + '/' + '0'
310
+ else
311
+ url = @rapid_endpoint + request_path + '/' + request
312
+ end
313
+ url = URI.encode(url)
314
+
315
+ response = Message::TransactionProcess::TransQueryMsgProcess.process_post_msg(url, @api_key, @password)
316
+ Message::TransactionProcess::TransQueryMsgProcess.make_result(response)
317
+ rescue => e
318
+ @logger.error(e.to_s) if @logger
319
+ make_response_with_exception(e, QueryTransactionResponse)
320
+ end
321
+ end
322
+
323
+ # Finds an error code from the properties file
324
+ #
325
+ # @param [String] code
326
+ # @return [String] the error code
327
+ def self.find_error_code(code, language)
328
+ error_file = 'err_code_resource_' + language + '.yml'
329
+ begin
330
+ property_array = YAML.load_file(File.join(File.dirname(__FILE__), 'resources', error_file))
331
+ property_array.each do |h|
332
+ if code == h.keys.first
333
+ return h[h.keys.first]
334
+ end
335
+ end
336
+ return code
337
+ rescue
338
+ @logger.error "Load resource from file: #{error_file} error" if @logger
339
+ return ''
340
+ end
341
+ end
342
+
343
+ # Validates the Rapid API key, password and endpoint
344
+ def validate_api_param
345
+ set_valid(true)
346
+ if @api_key.nil? || @api_key.empty? || @password.nil? || @password.empty?
347
+ add_error_code(Constants::API_KEY_INVALID_ERROR_CODE)
348
+ set_valid(false)
349
+ end
350
+ if @rapid_endpoint.nil? || @rapid_endpoint.empty?
351
+ add_error_code(Constants::LIBRARY_NOT_HAVE_ENDPOINT_ERROR_CODE)
352
+ set_valid(false)
353
+ end
354
+ if @is_valid
355
+ begin
356
+ parser_endpoint_to_web_url
357
+ if !@list_error.nil?
358
+ @list_error.clear
359
+ end
360
+ set_valid(true)
361
+ @logger.info "Initiate client [#{@rapid_endpoint}] successful!" if @logger
362
+ rescue => e
363
+ @logger.error "Error setting Rapid endpoint #{e.backtrace.inspect}" if @logger
364
+ set_valid(false)
365
+ add_error_code(Constants::LIBRARY_NOT_HAVE_ENDPOINT_ERROR_CODE)
366
+ end
367
+ else
368
+ @logger.warn "Invald parameter passed to Rapid client" if @logger
369
+ end
370
+ end
371
+
372
+ # Converts an endpoint string to a URL
373
+ def parser_endpoint_to_web_url
374
+ # @type [String]
375
+ prop_name = nil
376
+ if Constants::RAPID_ENDPOINT_PRODUCTION.casecmp(@rapid_endpoint).zero?
377
+ prop_name = Constants::GLOBAL_RAPID_PRODUCTION_REST_URL_PARAM
378
+ elsif Constants::RAPID_ENDPOINT_SANDBOX.casecmp(@rapid_endpoint).zero?
379
+ prop_name = Constants::GLOBAL_RAPID_SANDBOX_REST_URL_PARAM
380
+ end
381
+ if prop_name.nil?
382
+ set_web_url(@rapid_endpoint)
383
+ else
384
+ property_array = YAML.load_file(File.join(File.dirname(__FILE__), 'resources', 'rapid-api.yml'))
385
+ property_array.each do |h|
386
+ if prop_name.casecmp(h.keys.first).zero?
387
+ set_web_url(h[h.keys.first])
388
+ end
389
+ end
390
+ if @web_url.nil?
391
+ fail Exception, "The endpoint #{prop_name} is invalid."
392
+ end
393
+ end
394
+ # verify_endpoint_url(@web_url) # this is unreliable
395
+ end
396
+
397
+ # Checks the Rapid endpoint url
398
+ #
399
+ # @param [String] web_url
400
+ def verify_endpoint_url(web_url)
401
+ begin
402
+ resource = RestClient::Resource.new web_url
403
+ resource.get
404
+ rescue RestClient::Exception => e
405
+ if e.http_code == 404
406
+ set_valid(false)
407
+ end
408
+ end
409
+ end
410
+
411
+ # @param [String] error_code
412
+ def add_error_code(error_code)
413
+ if error_code
414
+ if @list_error.nil?
415
+ @list_error = []
416
+ @list_error.push(error_code)
417
+ else
418
+ unless @list_error.include? error_code
419
+ @list_error.push(error_code)
420
+ end
421
+ end
422
+ end
423
+ end
424
+
425
+ # @param [Boolean] is_valid
426
+ def set_valid(is_valid)
427
+ @is_valid = is_valid
428
+ end
429
+
430
+ # @param [String] web_url
431
+ def set_web_url(web_url)
432
+ @web_url = web_url
433
+ end
434
+
435
+ # @param [RapidSdkException] rapid_exception Exception to output
436
+ # @param [ResponseOutput] klass Output class to use for response
437
+ # @return [ResponseOutput]
438
+ def make_response_with_exception(rapid_exception, klass)
439
+ response_output = klass.new
440
+ response_output.errors.push(rapid_exception.error_code)
441
+ response_output
442
+ end
443
+ end
444
+ end