judopay 1.0.2.pre → 2.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 (63) hide show
  1. checksums.yaml +4 -4
  2. data/.travis.yml +6 -0
  3. data/CHANGELOG.md +3 -0
  4. data/README.md +2 -0
  5. data/Rakefile +17 -2
  6. data/judopay.gemspec +11 -10
  7. data/lib/faraday/raise_http_exception.rb +1 -18
  8. data/lib/judopay.rb +12 -9
  9. data/lib/judopay/connection.rb +28 -18
  10. data/lib/judopay/core_ext/string.rb +4 -3
  11. data/lib/judopay/error.rb +55 -97
  12. data/lib/judopay/model.rb +49 -40
  13. data/lib/judopay/models/card_payment.rb +5 -10
  14. data/lib/judopay/models/card_preauth.rb +1 -1
  15. data/lib/judopay/models/collection.rb +1 -1
  16. data/lib/judopay/models/refund.rb +1 -1
  17. data/lib/judopay/models/register_card.rb +28 -0
  18. data/lib/judopay/models/save_card.rb +26 -0
  19. data/lib/judopay/models/token_payment.rb +1 -0
  20. data/lib/judopay/models/void.rb +19 -0
  21. data/lib/judopay/models/web_payments/payment.rb +3 -0
  22. data/lib/judopay/models/web_payments/web_payment_operation.rb +8 -0
  23. data/lib/judopay/request.rb +1 -1
  24. data/lib/judopay/serializer.rb +1 -5
  25. data/lib/judopay/version.rb +2 -1
  26. data/spec/factories.rb +64 -19
  27. data/spec/faraday/response_spec.rb +10 -12
  28. data/spec/fixtures/card_payments/create_bad_request.json +11 -4
  29. data/spec/fixtures/transactions/register_card.json +29 -0
  30. data/spec/fixtures/transactions/save_card.json +28 -0
  31. data/spec/fixtures/transactions/void.json +27 -0
  32. data/spec/judopay/card_address_spec.rb +1 -1
  33. data/spec/judopay/card_payment_spec.rb +1 -2
  34. data/spec/judopay/collection_spec.rb +1 -1
  35. data/spec/judopay/error_spec.rb +36 -15
  36. data/spec/judopay/judopay_spec.rb +1 -1
  37. data/spec/judopay/market/collection_spec.rb +1 -1
  38. data/spec/judopay/market/payment_spec.rb +1 -1
  39. data/spec/judopay/market/preauth_spec.rb +1 -1
  40. data/spec/judopay/market/refund_spec.rb +1 -1
  41. data/spec/judopay/market/transaction_spec.rb +1 -1
  42. data/spec/judopay/payment_spec.rb +1 -1
  43. data/spec/judopay/preauth_spec.rb +1 -1
  44. data/spec/judopay/refund_spec.rb +1 -1
  45. data/spec/judopay/register_card_spec.rb +24 -0
  46. data/spec/judopay/save_card_spec.rb +23 -0
  47. data/spec/judopay/transaction_spec.rb +1 -1
  48. data/spec/judopay/void_spec.rb +24 -0
  49. data/spec/spec_helper.rb +6 -2
  50. data/test/authentication_test.rb +23 -0
  51. data/test/base/integration_base.rb +20 -0
  52. data/test/base/payments_tests.rb +40 -0
  53. data/test/base/token_payment_tests.rb +91 -0
  54. data/test/card_details_test.rb +21 -0
  55. data/test/configuration_test.rb +35 -0
  56. data/test/helper/assertion_helper.rb +29 -0
  57. data/test/payment_test.rb +10 -0
  58. data/test/preauth_test.rb +10 -0
  59. data/test/register_card_test.rb +37 -0
  60. data/test/token_payment_test.rb +10 -0
  61. data/test/token_preauth_test.rb +10 -0
  62. data/test/void_test.rb +44 -0
  63. metadata +107 -50
data/lib/judopay/model.rb CHANGED
@@ -9,45 +9,73 @@ module Judopay
9
9
  class Model
10
10
  send :include, Virtus.model
11
11
  include ActiveModel::Validations
12
- VALID_PAGING_OPTIONS = [:sort, :offset, :page_size]
12
+ VALID_PAGING_OPTIONS = [:sort, :offset, :page_size].freeze
13
13
 
14
14
  class << self
15
15
  @resource_path = nil
16
16
  @valid_api_methods = []
17
17
  attr_accessor :resource_path, :valid_api_methods
18
- end
19
18
 
20
- # List all records
21
- #
22
- # @param options [Hash] Paging options (sort, offset and page_size)
23
- # @return [Judopay::Mash] Mash of the API response
24
- def self.all(options = {})
25
- check_api_method_is_supported(__method__)
26
- api = Judopay::API.new
27
- valid_options = self.valid_options(options).camel_case_keys!
28
- uri = resource_path + '?' + valid_options.to_query_string
29
- api.get(uri)
19
+ # List all records
20
+ #
21
+ # @param options [Hash] Paging options (sort, offset and page_size)
22
+ # @return [Judopay::Mash] Mash of the API response
23
+ def all(options = {})
24
+ check_api_method_is_supported(__method__)
25
+ api = Judopay::API.new
26
+ valid_options = self.valid_options(options).camel_case_keys!
27
+ uri = resource_path + '?' + valid_options.to_query_string
28
+ api.get(uri)
29
+ end
30
+
31
+ # Retrieve a specific record
32
+ #
33
+ # @param receipt_id [Integer] ID of particular transaction
34
+ # @return [Judopay::Mash] Mash of the API response
35
+ def find(receipt_id)
36
+ check_api_method_is_supported(__method__)
37
+ api = Judopay::API.new
38
+ api.get(resource_path + receipt_id.to_i.to_s)
39
+ end
40
+
41
+ # Check if the specified API method is supported by the current model
42
+ #
43
+ # @raise [Judopay::Error] if the API method is not supported
44
+ def check_api_method_is_supported(method)
45
+ raise Judopay::ValidationError, 'API method not supported' if valid_api_methods.nil? || !valid_api_methods.include?(method.to_sym)
46
+ end
47
+
48
+ # Take an paging options hash and filter all but the valid keys
49
+ def valid_options(options)
50
+ valid_options = {}
51
+ options.each do |key, value|
52
+ next unless VALID_PAGING_OPTIONS.include?(key)
53
+ valid_options[key] = value
54
+ end
55
+ valid_options
56
+ end
30
57
  end
31
58
 
32
- # Retrieve a specific record
59
+ # Create a new record
33
60
  #
34
- # @param receipt_id [Integer] Paging options (sort, offset and page_size)
35
61
  # @return [Judopay::Mash] Mash of the API response
36
- def self.find(receipt_id)
62
+ def create
37
63
  check_api_method_is_supported(__method__)
64
+ check_judo_id
65
+ check_validation
38
66
  api = Judopay::API.new
39
- api.get(resource_path + receipt_id.to_i.to_s)
67
+ api.post(resource_path, self)
40
68
  end
41
69
 
42
- # Create a new record
70
+ # Validates a request
43
71
  #
44
72
  # @return [Judopay::Mash] Mash of the API response
45
- def create
73
+ def validate
46
74
  check_api_method_is_supported(__method__)
47
75
  check_judo_id
48
76
  check_validation
49
77
  api = Judopay::API.new
50
- api.post(resource_path, self)
78
+ api.post(resource_path + '/validate', self)
51
79
  end
52
80
 
53
81
  # Retrieve the current API resource path (e.g. /transactions/payments)
@@ -72,7 +100,7 @@ module Judopay
72
100
 
73
101
  # Use judo_id from configuration if it hasn't been explicitly set
74
102
  def check_judo_id
75
- return unless self.respond_to?('judo_id') && judo_id.nil?
103
+ return unless respond_to?('judo_id') && judo_id.nil?
76
104
  self.judo_id = Judopay.configuration.judo_id
77
105
  end
78
106
 
@@ -84,26 +112,7 @@ module Judopay
84
112
  # @return nil
85
113
  # @raise [Judopay::ValidationError] if there are validation errors on the model
86
114
  def check_validation
87
- fail Judopay::ValidationError, errors unless valid?
88
- end
89
-
90
- # Check if the specified API method is supported by the current model
91
- #
92
- # @raise [Judopay::Error] if the API method is not supported
93
- def self.check_api_method_is_supported(method)
94
- if valid_api_methods.nil? || !valid_api_methods.include?(method.to_sym)
95
- fail Judopay::Error, 'API method not supported'
96
- end
97
- end
98
-
99
- # Take an paging options hash and filter all but the valid keys
100
- def self.valid_options(options)
101
- valid_options = {}
102
- options.each do |key, value|
103
- next unless VALID_PAGING_OPTIONS.include?(key)
104
- valid_options[key] = value
105
- end
106
- valid_options
115
+ raise Judopay::ValidationError.new('Missing required fields', errors) unless valid?
107
116
  end
108
117
  end
109
118
  end
@@ -6,7 +6,7 @@ require_relative 'consumer_location'
6
6
  module Judopay
7
7
  class CardPayment < Model
8
8
  @resource_path = 'transactions/payments'
9
- @valid_api_methods = [:create]
9
+ @valid_api_methods = [:create, :validate]
10
10
 
11
11
  attribute :your_consumer_reference, String # required
12
12
  attribute :your_payment_reference, String # required
@@ -15,11 +15,12 @@ module Judopay
15
15
  attribute :amount, Float # required
16
16
  attribute :card_number, String # required for card transactions
17
17
  attribute :expiry_date, String # required for card transactions
18
- attribute :cv2, String # required for card transactions
18
+ attribute :cv2, String # required for card transactions
19
19
  attribute :card_address, Judopay::CardAddress
20
20
  attribute :consumer_location, Judopay::ConsumerLocation
21
21
  attribute :mobile_number, String
22
22
  attribute :email_address, String
23
+ attribute :currency, String
23
24
 
24
25
  validates_presence_of :your_consumer_reference,
25
26
  :your_payment_reference,
@@ -27,13 +28,7 @@ module Judopay
27
28
  :amount,
28
29
  :card_number,
29
30
  :expiry_date,
30
- :cv2
31
-
32
- def validate
33
- check_judo_id
34
- check_validation
35
- api = Judopay::API.new
36
- api.post(resource_path + '/validate', self)
37
- end
31
+ :cv2,
32
+ :currency
38
33
  end
39
34
  end
@@ -7,6 +7,6 @@ module Judopay
7
7
  # Inherit from CardPayment - attributes are identical
8
8
  class CardPreauth < CardPayment
9
9
  @resource_path = 'transactions/preauths'
10
- @valid_api_methods = [:create]
10
+ @valid_api_methods = [:create, :validate]
11
11
  end
12
12
  end
@@ -3,7 +3,7 @@ require_relative '../model'
3
3
  module Judopay
4
4
  class Collection < Model
5
5
  @resource_path = 'transactions/collections'
6
- @valid_api_methods = [:all, :create]
6
+ @valid_api_methods = [:all, :create, :validate]
7
7
 
8
8
  attribute :receipt_id, Integer
9
9
  attribute :amount, Float
@@ -3,7 +3,7 @@ require_relative '../model'
3
3
  module Judopay
4
4
  class Refund < Model
5
5
  @resource_path = 'transactions/refunds'
6
- @valid_api_methods = [:all, :create]
6
+ @valid_api_methods = [:all, :create, :validate]
7
7
 
8
8
  attribute :receipt_id, Integer
9
9
  attribute :amount, Float
@@ -0,0 +1,28 @@
1
+ require_relative '../model'
2
+ require_relative 'payment'
3
+ require_relative 'card_address'
4
+ require_relative 'consumer_location'
5
+
6
+ module Judopay
7
+ class RegisterCard < Model
8
+ @resource_path = 'transactions/registercard'
9
+ @valid_api_methods = [:create]
10
+
11
+ attribute :your_consumer_reference, String
12
+ attribute :your_payment_reference, String
13
+ attribute :card_number, String
14
+ attribute :expiry_date, String
15
+ attribute :cv2, String
16
+ attribute :card_address, Judopay::CardAddress
17
+ attribute :amount, Float
18
+ attribute :currency, String
19
+ attribute :judo_id, String
20
+ attribute :your_payment_meta_data, Hash
21
+
22
+ validates_presence_of :your_consumer_reference,
23
+ :your_payment_reference,
24
+ :card_number,
25
+ :expiry_date,
26
+ :cv2
27
+ end
28
+ end
@@ -0,0 +1,26 @@
1
+ require_relative '../model'
2
+ require_relative 'payment'
3
+ require_relative 'card_address'
4
+ require_relative 'consumer_location'
5
+
6
+ module Judopay
7
+ class SaveCard < Model
8
+ @resource_path = 'transactions/savecard'
9
+ @valid_api_methods = [:create]
10
+
11
+ attribute :your_consumer_reference, String
12
+ attribute :judo_id, String
13
+ attribute :card_number, String
14
+ attribute :expiry_date, String
15
+ attribute :string_date, String
16
+ attribute :issue_number, String
17
+ attribute :cv2, String
18
+ attribute :card_address, Judopay::CardAddress
19
+ attribute :currency, String
20
+
21
+ validates_presence_of :your_consumer_reference,
22
+ :card_number,
23
+ :expiry_date,
24
+ :cv2
25
+ end
26
+ end
@@ -19,6 +19,7 @@ module Judopay
19
19
  attribute :consumer_location, Judopay::ConsumerLocation
20
20
  attribute :mobile_number, String
21
21
  attribute :email_address, String
22
+ attribute :currency, String
22
23
 
23
24
  validates_presence_of :your_consumer_reference,
24
25
  :your_payment_reference,
@@ -0,0 +1,19 @@
1
+ require_relative '../model'
2
+
3
+ module Judopay
4
+ class Void < Model
5
+ @resource_path = 'transactions/voids'
6
+ @valid_api_methods = [:create, :validate]
7
+
8
+ attribute :judo_id, String
9
+ attribute :receipt_id, Integer
10
+ attribute :amount, Float
11
+ attribute :your_payment_reference, String
12
+ attribute :your_payment_meta_data, Hash
13
+ attribute :currency, String
14
+
15
+ validates_presence_of :receipt_id,
16
+ :amount,
17
+ :judo_id
18
+ end
19
+ end
@@ -1,4 +1,5 @@
1
1
  require_relative '../../model'
2
+ require_relative 'web_payment_operation'
2
3
 
3
4
  module Judopay
4
5
  module WebPayments
@@ -14,6 +15,8 @@ module Judopay
14
15
  attribute :your_payment_meta_data, Hash
15
16
  attribute :client_ip_address, String
16
17
  attribute :client_user_agent, String
18
+ attribute :currency, String
19
+ attribute :web_payment_operation, Judopay::WebPayments::WebPaymentOperation
17
20
 
18
21
  validates_presence_of :judo_id,
19
22
  :your_consumer_reference,
@@ -0,0 +1,8 @@
1
+ module Judopay
2
+ module WebPayments
3
+ module WebPaymentOperation
4
+ PAYMENT = 0
5
+ REGISTER = 1
6
+ end
7
+ end
8
+ end
@@ -15,7 +15,7 @@ module Judopay
15
15
  end
16
16
 
17
17
  # Perform an HTTP PUT request
18
- def put(path, options = {}, raw = false)
18
+ def put(path, options = {}, raw = false)
19
19
  request(:put, path, options, raw)
20
20
  end
21
21
 
@@ -19,11 +19,7 @@ module Judopay
19
19
  next if value.nil?
20
20
 
21
21
  # Is this a Virtus model object that we need to hashify?
22
- if value.class.included_modules.include?(Virtus::Model::Core)
23
- output_hash[key] = hashify(value)
24
- else
25
- output_hash[key] = value
26
- end
22
+ output_hash[key] = value.class.included_modules.include?(Virtus::Model::Core) ? hashify(value) : value
27
23
  end
28
24
  output_hash
29
25
  end
@@ -1,3 +1,4 @@
1
1
  module Judopay
2
- VERSION = '1.0.2.pre'
2
+ SDK_VERSION = '2.0.0'.freeze
3
+ API_VERSION = '5.2.0'.freeze
3
4
  end
data/spec/factories.rb CHANGED
@@ -8,32 +8,39 @@ models = %w(
8
8
  web_payments/payment
9
9
  market/collection
10
10
  market/refund
11
+ save_card
12
+ register_card
13
+ void
11
14
  )
12
15
  models.each { |model| require_relative '../lib/judopay/models/' + model }
13
16
 
14
17
  FactoryGirl.define do
15
- trait :valid_card_details do
18
+ trait :payment_details do
16
19
  your_consumer_reference 123
17
20
  your_payment_reference 456
18
- judo_id '123-456'
19
21
  amount 1.01
22
+ end
23
+
24
+ trait :valid_card do
20
25
  card_number '4976000000003436'
21
- expiry_date '12/15'
26
+ expiry_date '12/20'
22
27
  cv2 452
23
28
  end
24
29
 
30
+ trait :declined_card do
31
+ card_number '4221690000004963'
32
+ expiry_date '12/20'
33
+ cv2 125
34
+ end
35
+
25
36
  trait :valid_token_details do
26
- your_consumer_reference '123'
27
- your_payment_reference '456'
28
- judo_id '123-456'
29
- amount 1.01
30
37
  consumer_token '3UW4DV9wI0oKkMFS'
31
38
  card_token 'SXw4hnv1vJuEujQR'
32
- cv2 '452'
39
+ cv2 452
33
40
  end
34
41
 
35
42
  trait :valid_judo_id do
36
- judo_id '123-456'
43
+ judo_id '100435-197'
37
44
  end
38
45
 
39
46
  trait :valid_collection_or_refund_details do
@@ -48,13 +55,27 @@ FactoryGirl.define do
48
55
  end
49
56
 
50
57
  factory :card_payment, :class => Judopay::CardPayment do
51
- valid_card_details
58
+ payment_details
52
59
  valid_judo_id
60
+ valid_card
61
+ currency 'GBP'
62
+
63
+ trait :declined do
64
+ card_number '4221690000004963'
65
+ cv2 125
66
+ end
53
67
  end
54
68
 
55
69
  factory :card_preauth, :class => Judopay::CardPreauth do
56
- valid_card_details
70
+ payment_details
71
+ valid_card
57
72
  valid_judo_id
73
+ currency 'GBP'
74
+
75
+ trait :declined do
76
+ card_number '4221690000004963'
77
+ cv2 125
78
+ end
58
79
  end
59
80
 
60
81
  factory :collection, :class => Judopay::Collection do
@@ -66,31 +87,33 @@ FactoryGirl.define do
66
87
  end
67
88
 
68
89
  factory :token_payment, :class => Judopay::TokenPayment do
90
+ payment_details
69
91
  valid_token_details
70
92
  valid_judo_id
93
+ currency 'GBP'
71
94
  end
72
95
 
73
96
  factory :token_preauth, :class => Judopay::TokenPreauth do
97
+ payment_details
74
98
  valid_token_details
75
99
  valid_judo_id
100
+ currency 'GBP'
76
101
  end
77
102
 
78
103
  factory :web_payment, :class => Judopay::WebPayments::Payment do
79
104
  valid_judo_id
80
- amount 12.34
81
- partner_service_fee 1.00
82
- your_payment_reference '123'
83
- your_consumer_reference '456'
105
+ payment_details
84
106
  client_ip_address_and_user_agent
107
+
108
+ partner_service_fee 1.00
85
109
  end
86
110
 
87
111
  factory :web_preauth, :class => Judopay::WebPayments::Payment do
88
112
  valid_judo_id
89
- amount 12.34
90
- partner_service_fee 1.00
91
- your_payment_reference '123'
92
- your_consumer_reference '456'
113
+ payment_details
93
114
  client_ip_address_and_user_agent
115
+
116
+ partner_service_fee 1.00
94
117
  end
95
118
 
96
119
  factory :market_collection, :class => Judopay::Market::Collection do
@@ -100,4 +123,26 @@ FactoryGirl.define do
100
123
  factory :market_refund, :class => Judopay::Market::Refund do
101
124
  valid_collection_or_refund_details
102
125
  end
126
+
127
+ factory :save_card, :class => Judopay::SaveCard do
128
+ valid_card
129
+
130
+ your_consumer_reference 123
131
+ end
132
+
133
+ factory :register_card, :class => Judopay::RegisterCard do
134
+ payment_details
135
+ valid_card
136
+ valid_judo_id
137
+ currency 'GBP'
138
+
139
+ trait :declined do
140
+ card_number '4221690000004963'
141
+ cv2 125
142
+ end
143
+ end
144
+
145
+ factory :void, :class => Judopay::Void do
146
+ valid_collection_or_refund_details
147
+ end
103
148
  end