vantiv 0.3.0 → 1.0.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.
Files changed (220) hide show
  1. checksums.yaml +4 -4
  2. data/.codeclimate.yml +16 -0
  3. data/.env.example +4 -2
  4. data/.rubocop.yml +1157 -0
  5. data/.ruby-version +1 -1
  6. data/CHANGELOG.md +10 -0
  7. data/README.md +42 -29
  8. data/bin/console +5 -3
  9. data/bin/generate_sandbox_fixtures +5 -3
  10. data/bin/paypage_server +5 -3
  11. data/cert_fixtures/{L_AU_1.json → ACCOUNT_UPDATER_100.json} +0 -0
  12. data/cert_fixtures/{L_AU_3.json → ACCOUNT_UPDATER_100A.json} +0 -0
  13. data/cert_fixtures/{L_AU_7.json → ACCOUNT_UPDATER_100B.json} +1 -1
  14. data/cert_fixtures/{L_AU_2.json → ACCOUNT_UPDATER_101.json} +0 -0
  15. data/cert_fixtures/{L_AU_4.json → ACCOUNT_UPDATER_101A.json} +0 -0
  16. data/cert_fixtures/{L_AU_5.json → ACCOUNT_UPDATER_102.json} +0 -0
  17. data/cert_fixtures/{L_AU_6.json → ACCOUNT_UPDATER_103.json} +0 -0
  18. data/cert_fixtures/{L_AC_1.json → AUTH_CAPTURE_1.json} +0 -0
  19. data/cert_fixtures/AUTH_CAPTURE_1A.json +8 -0
  20. data/cert_fixtures/{L_AC_2.json → AUTH_CAPTURE_2.json} +0 -0
  21. data/cert_fixtures/AUTH_CAPTURE_2A.json +8 -0
  22. data/cert_fixtures/{L_AC_3.json → AUTH_CAPTURE_3.json} +0 -0
  23. data/cert_fixtures/AUTH_CAPTURE_3A.json +8 -0
  24. data/cert_fixtures/{L_AC_4.json → AUTH_CAPTURE_4.json} +0 -0
  25. data/cert_fixtures/AUTH_CAPTURE_4A.json +8 -0
  26. data/cert_fixtures/{L_AC_5.json → AUTH_CAPTURE_5.json} +0 -0
  27. data/cert_fixtures/AUTH_CAPTURE_5A.json +8 -0
  28. data/cert_fixtures/{L_AC_6.json → AUTH_CAPTURE_6.json} +0 -0
  29. data/cert_fixtures/{L_AC_7.json → AUTH_CAPTURE_7.json} +0 -0
  30. data/cert_fixtures/{L_AC_8.json → AUTH_CAPTURE_8.json} +0 -0
  31. data/cert_fixtures/{L_AC_9.json → AUTH_CAPTURE_9.json} +0 -0
  32. data/cert_fixtures/{L_AR_1.json → AUTH_REVERSAL_32.json} +0 -0
  33. data/cert_fixtures/{L_AR_1A.json → AUTH_REVERSAL_32A.json} +1 -1
  34. data/cert_fixtures/AUTH_REVERSAL_32B.json +8 -0
  35. data/cert_fixtures/{L_AR_2.json → AUTH_REVERSAL_33.json} +0 -0
  36. data/cert_fixtures/AUTH_REVERSAL_33A.json +8 -0
  37. data/cert_fixtures/{L_AR_3.json → AUTH_REVERSAL_34.json} +0 -0
  38. data/cert_fixtures/AUTH_REVERSAL_34A.json +8 -0
  39. data/cert_fixtures/{L_AR_4.json → AUTH_REVERSAL_35.json} +0 -0
  40. data/cert_fixtures/{L_AR_4A.json → AUTH_REVERSAL_35A.json} +1 -1
  41. data/cert_fixtures/{L_AR_4B.json → AUTH_REVERSAL_35B.json} +1 -1
  42. data/cert_fixtures/{L_AR_5.json → AUTH_REVERSAL_36.json} +0 -0
  43. data/cert_fixtures/{L_AR_5A.json → AUTH_REVERSAL_36A.json} +1 -1
  44. data/cert_fixtures/{L_RC_1.json → CREDIT_1.json} +0 -0
  45. data/cert_fixtures/CREDIT_1A.json +8 -0
  46. data/cert_fixtures/CREDIT_1B.json +8 -0
  47. data/cert_fixtures/{L_RC_2.json → CREDIT_2.json} +0 -0
  48. data/cert_fixtures/CREDIT_2A.json +8 -0
  49. data/cert_fixtures/CREDIT_2B.json +8 -0
  50. data/cert_fixtures/{L_RC_3.json → CREDIT_3.json} +0 -0
  51. data/cert_fixtures/CREDIT_3A.json +8 -0
  52. data/cert_fixtures/CREDIT_3B.json +8 -0
  53. data/cert_fixtures/{L_RC_4.json → CREDIT_4.json} +0 -0
  54. data/cert_fixtures/CREDIT_4A.json +8 -0
  55. data/cert_fixtures/CREDIT_4B.json +8 -0
  56. data/cert_fixtures/{L_RC_5.json → CREDIT_5.json} +0 -0
  57. data/cert_fixtures/CREDIT_5A.json +8 -0
  58. data/cert_fixtures/CREDIT_5B.json +8 -0
  59. data/cert_fixtures/{L_RC_6.json → SALE_1.json} +0 -0
  60. data/cert_fixtures/{L_S_2.json → SALE_2.json} +0 -0
  61. data/cert_fixtures/{L_S_3.json → SALE_3.json} +0 -0
  62. data/cert_fixtures/{L_S_4.json → SALE_4.json} +0 -0
  63. data/cert_fixtures/{L_S_5.json → SALE_5.json} +0 -0
  64. data/cert_fixtures/{L_S_6.json → SALE_6.json} +0 -0
  65. data/cert_fixtures/{L_S_7.json → SALE_7.json} +0 -0
  66. data/cert_fixtures/{L_S_8.json → SALE_8.json} +0 -0
  67. data/cert_fixtures/{L_S_9.json → SALE_9.json} +0 -0
  68. data/cert_fixtures/{L_S_1.json → SECURITY_CODE_FILTER_R1.json} +9 -9
  69. data/cert_fixtures/SECURITY_CODE_FILTER_R2.json +27 -0
  70. data/cert_fixtures/{L_T_1.json → TOKENIZATION_1.json} +0 -0
  71. data/cert_fixtures/{L_T_10.json → TOKENIZATION_10.json} +0 -0
  72. data/cert_fixtures/{L_T_11.json → TOKENIZATION_11.json} +0 -0
  73. data/cert_fixtures/{L_T_2.json → TOKENIZATION_2.json} +0 -0
  74. data/cert_fixtures/{L_T_3.json → TOKENIZATION_3.json} +0 -0
  75. data/cert_fixtures/{L_T_4.json → TOKENIZATION_4.json} +0 -0
  76. data/cert_fixtures/{L_T_6.json → TOKENIZATION_6.json} +0 -0
  77. data/cert_fixtures/{L_T_7.json → TOKENIZATION_7.json} +0 -0
  78. data/cert_fixtures/{L_T_8.json → TOKENIZATION_8.json} +0 -0
  79. data/cert_fixtures/{L_T_9.json → TOKENIZATION_9.json} +1 -1
  80. data/cert_fixtures/{L_V_1.json → VOID_1.json} +0 -0
  81. data/cert_fixtures/VOID_1A.json +8 -0
  82. data/cert_fixtures/VOID_1B.json +8 -0
  83. data/cert_fixtures/VOID_1C.json +8 -0
  84. data/cert_fixtures/{L_V_2.json → VOID_2.json} +0 -0
  85. data/cert_fixtures/VOID_2A.json +8 -0
  86. data/cert_fixtures/{L_V_3.json → VOID_3.json} +0 -0
  87. data/cert_fixtures/VOID_3A.json +8 -0
  88. data/cert_fixtures/{L_V_4.json → VOID_4.json} +0 -0
  89. data/cert_fixtures/VOID_4A.json +8 -0
  90. data/cert_fixtures/{L_EP_1.json → ePROTECT_1.json} +0 -0
  91. data/cert_fixtures/{L_EP_2.json → ePROTECT_2.json} +0 -0
  92. data/cert_fixtures/{L_EP_3.json → ePROTECT_3.json} +0 -0
  93. data/cert_fixtures/{L_EP_4.json → ePROTECT_4.json} +1 -1
  94. data/cert_fixtures/{L_EP_5.json → ePROTECT_5.json} +1 -1
  95. data/cert_fixtures/{L_EP_6.json → ePROTECT_6.json} +0 -0
  96. data/cert_fixtures/{L_EP_7.json → ePROTECT_7.json} +0 -0
  97. data/exe/vantiv-certify-app +18 -12
  98. data/lib/monkey_patches/representable/xml.rb +12 -0
  99. data/lib/vantiv.rb +39 -14
  100. data/lib/vantiv/api.rb +13 -1
  101. data/lib/vantiv/api/account_updater_response.rb +24 -29
  102. data/lib/vantiv/api/address.rb +8 -0
  103. data/lib/vantiv/api/apple_pay_response.rb +9 -0
  104. data/lib/vantiv/api/capture_response.rb +1 -1
  105. data/lib/vantiv/api/card.rb +47 -0
  106. data/lib/vantiv/api/cardholder_authentication.rb +11 -0
  107. data/lib/vantiv/api/fraud_result.rb +7 -0
  108. data/lib/vantiv/api/live_transaction_response.rb +4 -5
  109. data/lib/vantiv/api/payment_account.rb +11 -0
  110. data/lib/vantiv/api/request.rb +72 -33
  111. data/lib/vantiv/api/request_body.rb +100 -97
  112. data/lib/vantiv/api/request_body_representer.rb +54 -0
  113. data/lib/vantiv/api/request_body_representer_xml.rb +19 -0
  114. data/lib/vantiv/api/response.rb +9 -29
  115. data/lib/vantiv/api/response_body.rb +12 -0
  116. data/lib/vantiv/api/response_body_representer.rb +23 -0
  117. data/lib/vantiv/api/response_body_representer_xml.rb +25 -0
  118. data/lib/vantiv/api/tied_transaction_response.rb +5 -5
  119. data/lib/vantiv/api/tokenization_response.rb +15 -9
  120. data/lib/vantiv/api/transaction.rb +42 -0
  121. data/lib/vantiv/api/transaction_request_representer_xml.rb +57 -0
  122. data/lib/vantiv/api/transaction_response.rb +9 -0
  123. data/lib/vantiv/api/transaction_response_representer.rb +64 -0
  124. data/lib/vantiv/api/transaction_response_representer_xml.rb +54 -0
  125. data/lib/vantiv/certification/paypage_server.rb +13 -2
  126. data/lib/vantiv/certification/response_cache.rb +4 -12
  127. data/lib/vantiv/certification/validation_test_runner.rb +29 -10
  128. data/lib/vantiv/mocked_sandbox.rb +3 -2
  129. data/lib/vantiv/mocked_sandbox/api_request.rb +56 -27
  130. data/lib/vantiv/mocked_sandbox/fixture_generator.rb +56 -50
  131. data/lib/vantiv/mocked_sandbox/fixtures/{auth--4457000300000007.json.erb → auth--4457000300000007.json} +18 -16
  132. data/lib/vantiv/mocked_sandbox/fixtures/{auth--4457000301100004.json.erb → auth--4457000301100004.json} +16 -14
  133. data/lib/vantiv/mocked_sandbox/fixtures/{auth--4457002100000005.json.erb → auth--4457002100000005.json} +10 -10
  134. data/lib/vantiv/mocked_sandbox/fixtures/{auth--4457010000000009.json.erb → auth--4457010000000009.json} +11 -11
  135. data/lib/vantiv/mocked_sandbox/fixtures/{auth--5112000101110009.json.erb → auth--5112000101110009.json} +16 -16
  136. data/lib/vantiv/mocked_sandbox/fixtures/{auth--5112001600000006.json.erb → auth--5112001600000006.json} +10 -10
  137. data/lib/vantiv/mocked_sandbox/fixtures/{auth--5112001900000003.json.erb → auth--5112001900000003.json} +10 -10
  138. data/lib/vantiv/mocked_sandbox/fixtures/{auth_capture--4457000300000007.json.erb → auth_capture--4457000300000007.json} +18 -16
  139. data/lib/vantiv/mocked_sandbox/fixtures/{auth_capture--4457000301100004.json.erb → auth_capture--4457000301100004.json} +16 -14
  140. data/lib/vantiv/mocked_sandbox/fixtures/{auth_capture--4457002100000005.json.erb → auth_capture--4457002100000005.json} +10 -10
  141. data/lib/vantiv/mocked_sandbox/fixtures/{auth_capture--4457010000000009.json.erb → auth_capture--4457010000000009.json} +11 -11
  142. data/lib/vantiv/mocked_sandbox/fixtures/{auth_capture--5112000101110009.json.erb → auth_capture--5112000101110009.json} +16 -16
  143. data/lib/vantiv/mocked_sandbox/fixtures/{auth_capture--5112001600000006.json.erb → auth_capture--5112001600000006.json} +10 -10
  144. data/lib/vantiv/mocked_sandbox/fixtures/{auth_capture--5112001900000003.json.erb → auth_capture--5112001900000003.json} +10 -10
  145. data/lib/vantiv/mocked_sandbox/fixtures/auth_reversal.json +21 -0
  146. data/lib/vantiv/mocked_sandbox/fixtures/capture.json +21 -0
  147. data/lib/vantiv/mocked_sandbox/fixtures/credit.json +21 -0
  148. data/lib/vantiv/mocked_sandbox/fixtures/refund--4457000300000007.json +22 -0
  149. data/lib/vantiv/mocked_sandbox/fixtures/refund--4457000301100004.json +22 -0
  150. data/lib/vantiv/mocked_sandbox/fixtures/refund--4457002100000005.json +22 -0
  151. data/lib/vantiv/mocked_sandbox/fixtures/refund--4457010000000009.json +22 -0
  152. data/lib/vantiv/mocked_sandbox/fixtures/refund--5112000101110009.json +22 -0
  153. data/lib/vantiv/mocked_sandbox/fixtures/refund--5112001600000006.json +22 -0
  154. data/lib/vantiv/mocked_sandbox/fixtures/refund--5112001900000003.json +22 -0
  155. data/lib/vantiv/mocked_sandbox/fixtures/tokenize--RGFQNCt6U1d1M21SeVByVTM4dHlHb1FsVkUrSmpnWXhNY0o5UkMzRlZFanZiUHVnYjN1enJXbG1WSDF4aXlNc.json +17 -0
  156. data/lib/vantiv/mocked_sandbox/fixtures/tokenize--mocked-valid-temporary-token.json +23 -0
  157. data/lib/vantiv/mocked_sandbox/fixtures/tokenize--pDZJcmd1VjNlYXNaSlRMTGpocVZQY1NWVXE4Z W5UTko4NU9KK3p1L1p1Vzg4YzVPQVlSUHNITG1 JN2I0Nzl.json +17 -0
  158. data/lib/vantiv/mocked_sandbox/fixtures/tokenize_by_direct_post--4457000300000007.json +23 -0
  159. data/lib/vantiv/mocked_sandbox/fixtures/tokenize_by_direct_post--4457000301100004.json +23 -0
  160. data/lib/vantiv/mocked_sandbox/fixtures/tokenize_by_direct_post--4457002100000005.json +23 -0
  161. data/lib/vantiv/mocked_sandbox/fixtures/tokenize_by_direct_post--4457010000000009.json +23 -0
  162. data/lib/vantiv/mocked_sandbox/fixtures/{tokenize_by_direct_post--4457010010900010.json.erb → tokenize_by_direct_post--4457010010900010.json} +8 -8
  163. data/lib/vantiv/mocked_sandbox/fixtures/tokenize_by_direct_post--5112000101110009.json +23 -0
  164. data/lib/vantiv/mocked_sandbox/fixtures/tokenize_by_direct_post--5112001600000006.json +23 -0
  165. data/lib/vantiv/mocked_sandbox/fixtures/tokenize_by_direct_post--5112001900000003.json +23 -0
  166. data/lib/vantiv/mocked_sandbox/fixtures/void.json +21 -0
  167. data/lib/vantiv/mocked_sandbox/mocked_response_representer.rb +11 -0
  168. data/lib/vantiv/paypage.rb +5 -1
  169. data/lib/vantiv/test_temporary_token.rb +20 -0
  170. data/lib/vantiv/version.rb +1 -1
  171. data/vantiv-ruby.gemspec +5 -1
  172. metadata +191 -129
  173. data/cert_fixtures/L_AC_1A.json +0 -8
  174. data/cert_fixtures/L_AC_2A.json +0 -8
  175. data/cert_fixtures/L_AC_3A.json +0 -8
  176. data/cert_fixtures/L_AC_4A.json +0 -8
  177. data/cert_fixtures/L_AC_5A.json +0 -8
  178. data/cert_fixtures/L_AR_1B.json +0 -8
  179. data/cert_fixtures/L_AR_2A.json +0 -8
  180. data/cert_fixtures/L_AR_3A.json +0 -8
  181. data/cert_fixtures/L_RC_1A.json +0 -8
  182. data/cert_fixtures/L_RC_1B.json +0 -8
  183. data/cert_fixtures/L_RC_2A.json +0 -8
  184. data/cert_fixtures/L_RC_2B.json +0 -8
  185. data/cert_fixtures/L_RC_3A.json +0 -8
  186. data/cert_fixtures/L_RC_3B.json +0 -8
  187. data/cert_fixtures/L_RC_4A.json +0 -8
  188. data/cert_fixtures/L_RC_4B.json +0 -8
  189. data/cert_fixtures/L_RC_5A.json +0 -8
  190. data/cert_fixtures/L_RC_5B.json +0 -8
  191. data/cert_fixtures/L_RC_6A.json +0 -8
  192. data/cert_fixtures/L_RC_7.json +0 -26
  193. data/cert_fixtures/L_RC_7A.json +0 -8
  194. data/cert_fixtures/L_RC_8.json +0 -18
  195. data/cert_fixtures/L_V_1A.json +0 -8
  196. data/cert_fixtures/L_V_1B.json +0 -8
  197. data/cert_fixtures/L_V_1C.json +0 -8
  198. data/cert_fixtures/L_V_2A.json +0 -8
  199. data/cert_fixtures/L_V_3A.json +0 -8
  200. data/cert_fixtures/L_V_4A.json +0 -8
  201. data/lib/vantiv/api/request_body_generator.rb +0 -43
  202. data/lib/vantiv/mocked_sandbox/dynamic_response_body.rb +0 -40
  203. data/lib/vantiv/mocked_sandbox/fixtures/auth_reversal.json.erb +0 -21
  204. data/lib/vantiv/mocked_sandbox/fixtures/capture.json.erb +0 -21
  205. data/lib/vantiv/mocked_sandbox/fixtures/credit.json.erb +0 -21
  206. data/lib/vantiv/mocked_sandbox/fixtures/refund--4457000300000007.json.erb +0 -22
  207. data/lib/vantiv/mocked_sandbox/fixtures/refund--4457000301100004.json.erb +0 -22
  208. data/lib/vantiv/mocked_sandbox/fixtures/refund--4457002100000005.json.erb +0 -22
  209. data/lib/vantiv/mocked_sandbox/fixtures/refund--4457010000000009.json.erb +0 -22
  210. data/lib/vantiv/mocked_sandbox/fixtures/refund--5112000101110009.json.erb +0 -22
  211. data/lib/vantiv/mocked_sandbox/fixtures/refund--5112001600000006.json.erb +0 -22
  212. data/lib/vantiv/mocked_sandbox/fixtures/refund--5112001900000003.json.erb +0 -22
  213. data/lib/vantiv/mocked_sandbox/fixtures/tokenize_by_direct_post--4457000300000007.json.erb +0 -23
  214. data/lib/vantiv/mocked_sandbox/fixtures/tokenize_by_direct_post--4457000301100004.json.erb +0 -23
  215. data/lib/vantiv/mocked_sandbox/fixtures/tokenize_by_direct_post--4457002100000005.json.erb +0 -23
  216. data/lib/vantiv/mocked_sandbox/fixtures/tokenize_by_direct_post--4457010000000009.json.erb +0 -23
  217. data/lib/vantiv/mocked_sandbox/fixtures/tokenize_by_direct_post--5112000101110009.json.erb +0 -23
  218. data/lib/vantiv/mocked_sandbox/fixtures/tokenize_by_direct_post--5112001600000006.json.erb +0 -23
  219. data/lib/vantiv/mocked_sandbox/fixtures/tokenize_by_direct_post--5112001900000003.json.erb +0 -23
  220. data/lib/vantiv/mocked_sandbox/fixtures/void.json.erb +0 -21
@@ -1,51 +1,46 @@
1
+ require "forwardable"
2
+
1
3
  module Vantiv
2
4
  module Api
3
- class AccountUpdaterResponse
4
- def initialize(account_updater)
5
- @account_updater_response = account_updater
6
- end
5
+ class CardTokenInfo
6
+ attr_accessor :payment_account_id, :card_type, :expiry_month, :expiry_year, :bin
7
7
 
8
- def payment_account_id
9
- new_card_token_info["PaymentAccountID"]
8
+ def expiry_date=(string)
9
+ @expiry_month = string[0..1]
10
+ @expiry_year = string[2..3]
10
11
  end
12
+ end
11
13
 
12
- def card_type
13
- new_card_token_info["Type"]
14
- end
14
+ class ExtendedCardResponse
15
+ attr_accessor :code, :message
16
+ end
15
17
 
16
- def expiry_month
17
- new_card_token_info["ExpirationMonth"]
18
- end
18
+ class AccountUpdaterResponse
19
+ extend Forwardable
19
20
 
20
- def expiry_year
21
- new_card_token_info["ExpirationYear"]
21
+ attr_accessor :original_card_token_info, :new_card_token_info, :extended_card_response
22
+
23
+ def initialize
24
+ @new_card_token_info = CardTokenInfo.new
25
+ @extended_card_response = ExtendedCardResponse.new
22
26
  end
23
27
 
28
+ def_delegators :new_card_token_info, :payment_account_id, :card_type, :expiry_month, :expiry_year
29
+
24
30
  def extended_card_response_code
25
- extended_card_response["code"]
31
+ extended_card_response.code
26
32
  end
27
33
 
28
34
  def extended_card_response_message
29
- extended_card_response["message"]
35
+ extended_card_response.message
30
36
  end
31
37
 
32
38
  def new_card_token?
33
- new_card_token_info.any?
39
+ !!payment_account_id
34
40
  end
35
41
 
36
42
  def extended_card_response?
37
- extended_card_response.any?
38
- end
39
-
40
- private
41
- attr_reader :account_updater_response
42
-
43
- def new_card_token_info
44
- account_updater_response.fetch("newCardTokenInfo", {})
45
- end
46
-
47
- def extended_card_response
48
- account_updater_response.fetch("extendedCardResponse", {})
43
+ !!extended_card_response_code || !!extended_card_response_message
49
44
  end
50
45
  end
51
46
  end
@@ -0,0 +1,8 @@
1
+ module Vantiv
2
+ module Api
3
+ class Address
4
+ attr_accessor :billing_name, :billing_address_1, :billing_address_2,
5
+ :billing_city, :billing_state, :billing_zipcode, :billing_country
6
+ end
7
+ end
8
+ end
@@ -0,0 +1,9 @@
1
+ module Vantiv
2
+ module Api
3
+ class ApplePayResponse
4
+ attr_accessor :online_payment_cryptogram
5
+ # if online_payment_cryptogram is present you must pass
6
+ # it in the next auth or sale transaction
7
+ end
8
+ end
9
+ end
@@ -19,7 +19,7 @@ module Vantiv
19
19
  private
20
20
 
21
21
  def transaction_response_name
22
- "captureResponse"
22
+ "capture_response"
23
23
  end
24
24
  end
25
25
  end
@@ -0,0 +1,47 @@
1
+ module Vantiv
2
+ module Api
3
+ class Card
4
+ attr_writer :cvv, :card_number, :account_number
5
+ attr_accessor :expiry_month, :expiry_year, :type, :paypage_registration_id, :payment_account_id
6
+
7
+ def initialize(expiry_month: nil, expiry_year: nil, cvv: nil, card_number: nil, account_number: nil, paypage_registration_id: nil)
8
+ @expiry_month = expiry_month
9
+ @expiry_year = expiry_year
10
+ @cvv = cvv
11
+ @card_number = card_number
12
+ @account_number = account_number
13
+ @paypage_registration_id = paypage_registration_id
14
+ end
15
+
16
+ def expiry_month
17
+ format_expiry(@expiry_month) if @expiry_month
18
+ end
19
+
20
+ def expiry_year
21
+ format_expiry(@expiry_year) if @expiry_year
22
+ end
23
+
24
+ def card_number
25
+ format_card_number(@card_number) if @card_number
26
+ end
27
+
28
+ def account_number
29
+ format_card_number(@account_number) if @account_number
30
+ end
31
+
32
+ def cvv
33
+ @cvv.to_s if @cvv
34
+ end
35
+
36
+ private
37
+
38
+ def format_expiry(raw_value)
39
+ raw_value.to_s.reverse[0..1].reverse.rjust(2, "0")
40
+ end
41
+
42
+ def format_card_number(card_number)
43
+ card_number.to_s.gsub(/\D*/, "") if card_number
44
+ end
45
+ end
46
+ end
47
+ end
@@ -0,0 +1,11 @@
1
+ module Vantiv
2
+ module Api
3
+ class CardholderAuthentication
4
+ attr_accessor :authentication_value
5
+
6
+ def initialize(authentication_value:)
7
+ @authentication_value = authentication_value
8
+ end
9
+ end
10
+ end
11
+ end
@@ -0,0 +1,7 @@
1
+ module Vantiv
2
+ module Api
3
+ class FraudResult
4
+ attr_accessor :avs_result, :card_validation_result
5
+ end
6
+ end
7
+ end
@@ -12,8 +12,8 @@ module Vantiv
12
12
  }.freeze
13
13
 
14
14
  LIVE_TRANSACTION_RESPONSE_NAMES = {
15
- auth: "authorizationResponse",
16
- sale: "saleResponse"
15
+ auth: "authorization_response",
16
+ sale: "sale_response"
17
17
  }
18
18
 
19
19
  def initialize(transaction_name)
@@ -43,9 +43,8 @@ module Vantiv
43
43
  end
44
44
 
45
45
  def account_updater
46
- @account_updater ||= AccountUpdaterResponse.new(
47
- litle_transaction_response.fetch("accountUpdater", {})
48
- )
46
+ @account_updater ||=
47
+ litle_transaction_response.account_updater || AccountUpdaterResponse.new
49
48
  end
50
49
 
51
50
  private
@@ -0,0 +1,11 @@
1
+ module Vantiv
2
+ module Api
3
+ class PaymentAccount
4
+ attr_accessor :id
5
+
6
+ def initialize(id: nil)
7
+ @id = id
8
+ end
9
+ end
10
+ end
11
+ end
@@ -1,74 +1,113 @@
1
1
  module Vantiv
2
2
  class Api::Request
3
-
4
3
  attr_reader :body
5
4
 
5
+ ENDPOINT_XML_TRANSACTION_TYPE = {
6
+ :"payment/sp2/credit/v1/authorization" => :authorization,
7
+ :"payment/sp2/credit/v1/authorizationCompletion" => :capture,
8
+ :"payment/sp2/credit/v1/reversal" => :authReversal,
9
+ :"payment/sp2/credit/v1/sale" => :sale,
10
+ :"payment/sp2/credit/v1/credit" => :credit,
11
+ :"payment/sp2/credit/v1/return" => :credit,
12
+ :"payment/sp2/services/v1/paymentAccountCreate" => :registerTokenRequest,
13
+ :"payment/sp2/credit/v1/void" => :void
14
+ }.freeze
15
+
6
16
  def initialize(endpoint:, body:, response_object:)
7
17
  @endpoint = endpoint
8
- @body = body.to_json
9
18
  @response_object = response_object
10
- self.retry_count = 0
19
+ @retry_count = 0
20
+
21
+ @body = populated_request_body(body)
11
22
  end
12
23
 
13
24
  def run
14
- vantiv_response = run_request_with_retries
15
- response_object.load(vantiv_response)
16
- response_object
25
+ run_request_with_retries
17
26
  end
18
27
 
19
28
  def run_request
20
- http = Net::HTTP.new(uri.host, uri.port)
21
- http.use_ssl = true
22
-
23
- request = Net::HTTP::Post.new(uri.request_uri, header)
24
- request.body = body
25
- raw_response = http.request(request)
26
- parsed_body = JSON.parse(raw_response.body)
27
- {
28
- httpok: raw_response.code_type == Net::HTTPOK,
29
- http_response_code: raw_response.code,
30
- body: parsed_body
31
- }
29
+ http_response = make_request
30
+ populated_response(@response_object, http_response)
32
31
  end
33
32
 
34
33
  private
35
34
 
36
- attr_reader :endpoint, :response_object
37
- attr_accessor :retry_count
35
+ def populated_request_body(body)
36
+ populated_body = body.dup
37
+
38
+ if populated_body.card && populated_body.payment_account
39
+ populated_body.card.payment_account_id = populated_body.payment_account.id
40
+ end
41
+
42
+ populated_body.transaction ||= Vantiv::Api::Transaction.new
43
+ populated_body.transaction.type = ENDPOINT_XML_TRANSACTION_TYPE.fetch(@endpoint.to_sym)
44
+ populated_body.transaction.address = populated_body.address
45
+ populated_body.transaction.card = populated_body.card if populated_body.card
46
+ populated_body.transaction.report_group = populated_body.report_group
47
+ populated_body.transaction.application_id = populated_body.application_id
48
+
49
+ populated_body.xmlns = "http://www.litle.com/schema"
50
+ populated_body.version = "10.2"
51
+
52
+ populated_body
53
+ end
54
+
55
+ def make_request
56
+ http = Net::HTTP.new(uri.host, uri.port)
57
+ http.use_ssl = true
58
+ request = Net::HTTP::Post.new(uri.request_uri, header)
59
+ request.body = body.to_xml
60
+ http.request(request)
61
+ end
38
62
 
39
63
  def header
40
64
  {
41
- "Content-Type" =>"application/json",
42
- "Authorization" => "VANTIV license=\"#{Vantiv.license_id}\""
65
+ "Content-Type" =>"text/xml"
43
66
  }
44
67
  end
45
68
 
46
69
  def uri
47
- @uri ||= URI.parse("#{root_uri}/#{endpoint}")
70
+ @uri ||= URI.parse("#{root_uri}/vap/communicator/online")
48
71
  end
49
72
 
50
73
  def root_uri
51
74
  if Vantiv::Environment.production?
52
- "https://apis.vantiv.com"
75
+ "https://transact.litle.com"
53
76
  elsif Vantiv::Environment.certification?
54
- "https://apis.cert.vantiv.com"
77
+ "https://transact-prelive.litle.com"
55
78
  end
56
79
  end
57
80
 
81
+ def populated_response(response, http_response)
82
+ new_response = response.dup
83
+
84
+ new_response.raw_body = http_response.body
85
+ new_response.httpok = http_response.code_type == Net::HTTPOK
86
+ new_response.http_response_code = http_response.code
87
+
88
+ response_body = ResponseBodyRepresenterXml.new(
89
+ Vantiv::Api::ResponseBody.new
90
+ ).from_xml(http_response.body)
91
+
92
+ new_response.body = response_body
93
+
94
+ new_response
95
+ end
96
+
97
+ def increment_retry_count
98
+ @retry_count += 1
99
+ end
100
+
58
101
  def max_retries_exceeded?
59
- retry_count > 3
102
+ @retry_count > 3
60
103
  end
61
104
 
62
105
  def run_request_with_retries
63
106
  begin
64
107
  run_request
65
- rescue JSON::ParserError => e
66
- self.retry_count += 1
67
- if max_retries_exceeded?
68
- raise e
69
- else
70
- run_request_with_retries
71
- end
108
+ rescue MultiJson::ParseError, Nokogiri::XML::SyntaxError => e
109
+ increment_retry_count
110
+ max_retries_exceeded? ? raise(e) : retry
72
111
  end
73
112
  end
74
113
  end
@@ -1,131 +1,134 @@
1
+ require 'securerandom'
2
+
1
3
  module Vantiv
2
4
  module Api
3
- module RequestBody
4
- def self.for_auth_or_sale(amount:, customer_id:, order_id:, payment_account_id:, expiry_month:, expiry_year:)
5
- RequestBodyGenerator.run(
6
- transaction_element(
7
- amount: amount,
8
- order_id: order_id,
9
- customer_id: customer_id
10
- ),
11
- card_element_for_live_transactions(
12
- expiry_month: expiry_month,
13
- expiry_year: expiry_year
14
- ),
15
- payment_account_element(payment_account_id: payment_account_id)
16
- )
5
+ class Authentication
6
+ attr_accessor :user, :password
7
+ def user
8
+ Vantiv.user
9
+ end
10
+ def password
11
+ Vantiv.password
17
12
  end
13
+ end
18
14
 
19
- def self.for_auth_reversal(transaction_id:, amount: nil)
20
- RequestBodyGenerator.run(
21
- tied_transaction_element(transaction_id: transaction_id, amount: amount)
22
- )
15
+ class RequestBody
16
+ attr_reader :merchant_id, :application_id, :report_group
17
+ attr_accessor :card, :transaction, :payment_account, :address
18
+
19
+ attr_accessor :version, :authentication, :xmlns
20
+
21
+ def initialize(card: nil, transaction: nil, payment_account: nil)
22
+ @card = card
23
+ @transaction = transaction
24
+ @payment_account = payment_account
25
+
26
+ @merchant_id = Vantiv.merchant_id
27
+ @application_id = SecureRandom.hex(12)
28
+ @report_group = Vantiv.default_report_group
29
+
30
+ @authentication = Authentication.new
23
31
  end
24
32
 
25
- def self.for_capture(transaction_id:, amount: nil)
26
- RequestBodyGenerator.run(
27
- tied_transaction_element(transaction_id: transaction_id, amount: amount)
28
- )
33
+ def to_json
34
+ ::RequestBodyRepresenter.new(self).to_json
29
35
  end
30
36
 
31
- def self.for_credit(transaction_id:, amount: nil)
32
- RequestBodyGenerator.run(
33
- tied_transaction_element(transaction_id: transaction_id, amount: amount)
34
- )
37
+ def to_xml
38
+ ::RequestBodyRepresenterXml.new(self).to_xml
35
39
  end
36
40
 
37
- def self.for_return(amount:, customer_id:, order_id:, payment_account_id:, expiry_month:, expiry_year:)
38
- transaction = transaction_element(
39
- amount: amount,
41
+ def self.for_auth_or_sale(amount:, customer_id:, order_id:, payment_account_id:,
42
+ expiry_month:, expiry_year:, cvv: nil, order_source: Vantiv.default_order_source,
43
+ online_payment_cryptogram: nil)
44
+
45
+
46
+ if online_payment_cryptogram
47
+ cardholder_authentication = CardholderAuthentication.new(
48
+ authentication_value: online_payment_cryptogram
49
+ )
50
+ else
51
+ cardholder_authentication = nil
52
+ end
53
+
54
+ transaction = Transaction.new(
40
55
  order_id: order_id,
41
- customer_id: customer_id
56
+ amount_in_cents: amount,
57
+ customer_id: customer_id,
58
+ order_source: order_source,
59
+ partial_approved_flag: false,
60
+ cardholder_authentication: cardholder_authentication
42
61
  )
43
- transaction["Transaction"].delete("PartialApprovedFlag")
44
- RequestBodyGenerator.run(
45
- transaction,
46
- card_element_for_live_transactions(
47
- expiry_month: expiry_month,
48
- expiry_year: expiry_year
49
- ),
50
- payment_account_element(payment_account_id: payment_account_id)
62
+ card = Card.new(
63
+ expiry_month: expiry_month,
64
+ expiry_year: expiry_year,
65
+ cvv: cvv
51
66
  )
52
- end
67
+ payment_account = PaymentAccount.new(id: payment_account_id)
53
68
 
54
- def self.for_tokenization(paypage_registration_id:)
55
- RequestBodyGenerator.run(
56
- card_element_for_tokenization(paypage_registration_id)
69
+ new(
70
+ transaction: transaction,
71
+ card: card,
72
+ payment_account: payment_account
57
73
  )
58
74
  end
59
75
 
60
- def self.for_direct_post_tokenization(card_number:, expiry_month:, expiry_year:, cvv:)
61
- RequestBodyGenerator.run(
62
- {
63
- "Card" => {
64
- "AccountNumber" => card_number.to_s.gsub(/\D*/, ""),
65
- "ExpirationMonth" => format_expiry(expiry_month),
66
- "ExpirationYear" => format_expiry(expiry_year),
67
- "CVV" => cvv.to_s
68
- }
69
- }
70
- )
76
+ def self.for_auth_reversal(transaction_id:, amount: nil)
77
+ transaction = Transaction.new(id: transaction_id, amount_in_cents: amount)
78
+ new(transaction: transaction)
71
79
  end
72
80
 
73
- def self.for_void(transaction_id:)
74
- RequestBodyGenerator.run(tied_transaction_element(transaction_id: transaction_id))
81
+ def self.for_capture(transaction_id:, amount: nil)
82
+ transaction = Transaction.new(id: transaction_id, amount_in_cents: amount)
83
+ new(transaction: transaction)
75
84
  end
76
85
 
77
- def self.card_element_for_tokenization(paypage_registration_id)
78
- {
79
- "Card" => {
80
- "PaypageRegistrationID" => paypage_registration_id
81
- }
82
- }
86
+ def self.for_credit(transaction_id:, amount: nil)
87
+ transaction = Transaction.new(id: transaction_id, amount_in_cents: amount)
88
+ new(transaction: transaction)
83
89
  end
84
90
 
85
- def self.card_element_for_live_transactions(expiry_month:, expiry_year:)
86
- {
87
- "Card" => {
88
- "ExpirationMonth" => format_expiry(expiry_month),
89
- "ExpirationYear" => format_expiry(expiry_year)
90
- }
91
- }
92
- end
91
+ def self.for_return(amount:, customer_id:, order_id:, payment_account_id:,
92
+ expiry_month:, expiry_year:, order_source: Vantiv.default_order_source)
93
+ transaction = Transaction.new(
94
+ order_id: order_id,
95
+ amount_in_cents: amount,
96
+ order_source: order_source,
97
+ customer_id: customer_id
98
+ )
99
+ card = Card.new(
100
+ expiry_month: expiry_month,
101
+ expiry_year: expiry_year
102
+ )
103
+ payment_account = PaymentAccount.new(id: payment_account_id)
93
104
 
94
- def self.tied_transaction_element(transaction_id:, amount: nil)
95
- res = {
96
- "Transaction" => {
97
- "TransactionID" => transaction_id
98
- }
99
- }
100
- if amount
101
- res["Transaction"]["TransactionAmount"] = '%.2f' % (amount / 100.0)
102
- end
103
- res
105
+ new(
106
+ transaction: transaction,
107
+ card: card,
108
+ payment_account: payment_account
109
+ )
104
110
  end
105
111
 
106
- def self.transaction_element(amount:, customer_id:, order_id:)
107
- {
108
- "Transaction" => {
109
- "ReferenceNumber" => order_id.to_s,
110
- "TransactionAmount" => '%.2f' % (amount / 100.0),
111
- "OrderSource" => Vantiv.order_source,
112
- "CustomerID" => customer_id,
113
- "PartialApprovedFlag" => false
114
- }
115
- }
112
+ def self.for_tokenization(paypage_registration_id:)
113
+ card = Card.new(paypage_registration_id: paypage_registration_id)
114
+ new(card: card)
116
115
  end
117
116
 
118
- def self.payment_account_element(payment_account_id:)
119
- {
120
- "PaymentAccount" => {
121
- "PaymentAccountID" => payment_account_id
122
- }
123
- }
117
+ def self.for_direct_post_tokenization(card_number:, expiry_month:, expiry_year:, cvv:)
118
+ card = Card.new(
119
+ account_number: card_number,
120
+ expiry_month: expiry_month,
121
+ expiry_year: expiry_year,
122
+ cvv: cvv
123
+ )
124
+ new(card: card)
124
125
  end
125
126
 
126
- def self.format_expiry(raw_value)
127
- raw_value.to_s.reverse[0..1].reverse.rjust(2, "0")
127
+ def self.for_void(transaction_id:)
128
+ transaction = Transaction.new(id: transaction_id)
129
+ new(transaction: transaction)
128
130
  end
131
+
129
132
  end
130
133
  end
131
134
  end