gocardless_pro 2.17.1 → 2.21.0

Sign up to get free protection for your applications and to get access to all the features.
Files changed (30) hide show
  1. checksums.yaml +4 -4
  2. data/lib/gocardless_pro.rb +3 -0
  3. data/lib/gocardless_pro/client.rb +6 -1
  4. data/lib/gocardless_pro/resources/creditor_bank_account.rb +1 -2
  5. data/lib/gocardless_pro/resources/currency_exchange_rate.rb +44 -0
  6. data/lib/gocardless_pro/resources/customer_notification.rb +3 -5
  7. data/lib/gocardless_pro/resources/event.rb +2 -1
  8. data/lib/gocardless_pro/resources/mandate_import.rb +5 -8
  9. data/lib/gocardless_pro/resources/mandate_import_entry.rb +3 -5
  10. data/lib/gocardless_pro/resources/payout.rb +2 -0
  11. data/lib/gocardless_pro/resources/redirect_flow.rb +2 -0
  12. data/lib/gocardless_pro/resources/subscription.rb +38 -29
  13. data/lib/gocardless_pro/services/currency_exchange_rates_service.rb +67 -0
  14. data/lib/gocardless_pro/services/customers_service.rb +1 -2
  15. data/lib/gocardless_pro/services/instalment_schedules_service.rb +81 -5
  16. data/lib/gocardless_pro/services/mandates_service.rb +1 -1
  17. data/lib/gocardless_pro/services/payouts_service.rb +21 -0
  18. data/lib/gocardless_pro/services/subscriptions_service.rb +129 -0
  19. data/lib/gocardless_pro/version.rb +1 -1
  20. data/spec/resources/currency_exchange_rate_spec.rb +103 -0
  21. data/spec/resources/instalment_schedule_spec.rb +193 -1
  22. data/spec/resources/payout_spec.rb +45 -0
  23. data/spec/resources/redirect_flow_spec.rb +9 -0
  24. data/spec/resources/subscription_spec.rb +210 -0
  25. data/spec/services/currency_exchange_rates_service_spec.rb +223 -0
  26. data/spec/services/instalment_schedules_service_spec.rb +270 -1
  27. data/spec/services/payouts_service_spec.rb +74 -0
  28. data/spec/services/redirect_flows_service_spec.rb +9 -0
  29. data/spec/services/subscriptions_service_spec.rb +240 -0
  30. metadata +9 -3
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: cb41d5906c1d6d6a9fc78abc852058cf63715020e3c957c7a0a8bcc8e907d74e
4
- data.tar.gz: c85a921b9ea881ed5acc7d56c20b4f75f5c51e1c5e305d4de8c7d0079798adbf
3
+ metadata.gz: 4c285e5a1284e099a2840ea4dfb7a8282a73a38aa0def7e81f522654b4be5922
4
+ data.tar.gz: 0443f073f12c0c6d69029a4a79d28634978274e73b6d1bc0a1517066c44b66e8
5
5
  SHA512:
6
- metadata.gz: 54114ab5751f18ea4c0b010ca600db89523de93353f309cd0e247dbc13a7339f1cf14d7869f44db7d7b0a7571233a54bd9bc0130c9c4eb796bf186bda5e659eb
7
- data.tar.gz: a2c5a5cdc5321d2e8a00f82adaba6b56540f3aa86d55cf950862f92fbc1cd971e5bad955b4701d69c4babb2fa5ac83a01a53f5da3427117ec7c11d652c47730e
6
+ metadata.gz: bf2401b3823b41bd1d562a80f0e7a8b0847a86f04e1ec29ad2e55b3caf814e39ea379f0686c6108b91de81701b8cebc697e0bd1f7cd4741c44176785c01bcc27
7
+ data.tar.gz: f8aa9bd7ff1c8f969d54ae654b324395572459ec065e603601dbe5eb9a38ec61852724820dc8423bc7407e47004434dcee4b880b3a4d2678086b0f0729dece07
@@ -47,6 +47,9 @@ require_relative 'gocardless_pro/services/creditors_service'
47
47
  require_relative 'gocardless_pro/resources/creditor_bank_account'
48
48
  require_relative 'gocardless_pro/services/creditor_bank_accounts_service'
49
49
 
50
+ require_relative 'gocardless_pro/resources/currency_exchange_rate'
51
+ require_relative 'gocardless_pro/services/currency_exchange_rates_service'
52
+
50
53
  require_relative 'gocardless_pro/resources/customer'
51
54
  require_relative 'gocardless_pro/services/customers_service'
52
55
 
@@ -18,6 +18,11 @@ module GoCardlessPro
18
18
  @creditor_bank_accounts ||= Services::CreditorBankAccountsService.new(@api_service)
19
19
  end
20
20
 
21
+ # Access to the service for currency_exchange_rate to make API calls
22
+ def currency_exchange_rates
23
+ @currency_exchange_rates ||= Services::CurrencyExchangeRatesService.new(@api_service)
24
+ end
25
+
21
26
  # Access to the service for customer to make API calls
22
27
  def customers
23
28
  @customers ||= Services::CustomersService.new(@api_service)
@@ -143,7 +148,7 @@ module GoCardlessPro
143
148
  'User-Agent' => user_agent.to_s,
144
149
  'Content-Type' => 'application/json',
145
150
  'GoCardless-Client-Library' => 'gocardless-pro-ruby',
146
- 'GoCardless-Client-Version' => '2.17.1',
151
+ 'GoCardless-Client-Version' => '2.21.0',
147
152
  },
148
153
  }
149
154
  end
@@ -23,8 +23,7 @@ module GoCardlessPro
23
23
  # `links[creditor_bank_account]` in the error response.
24
24
  #
25
25
  # <p class="restricted-notice"><strong>Restricted</strong>: This API is not
26
- # available for
27
- # partner integrations.</p>
26
+ # available for partner integrations.</p>
28
27
  class CreditorBankAccount
29
28
  attr_reader :account_holder_name
30
29
  attr_reader :account_number_ending
@@ -0,0 +1,44 @@
1
+ # encoding: utf-8
2
+
3
+ #
4
+ # This client is automatically generated from a template and JSON schema definition.
5
+ # See https://github.com/gocardless/gocardless-pro-ruby#contributing before editing.
6
+ #
7
+
8
+ require 'uri'
9
+
10
+ module GoCardlessPro
11
+ # A module containing classes for each of the resources in the GC Api
12
+ module Resources
13
+ # Represents an instance of a currency_exchange_rate resource returned from the API
14
+
15
+ # Currency exchange rates from our foreign exchange provider.
16
+ class CurrencyExchangeRate
17
+ attr_reader :rate
18
+ attr_reader :source
19
+ attr_reader :target
20
+ attr_reader :time
21
+
22
+ # Initialize a currency_exchange_rate resource instance
23
+ # @param object [Hash] an object returned from the API
24
+ def initialize(object, response = nil)
25
+ @object = object
26
+
27
+ @rate = object['rate']
28
+ @source = object['source']
29
+ @target = object['target']
30
+ @time = object['time']
31
+ @response = response
32
+ end
33
+
34
+ def api_response
35
+ ApiResponse.new(@response)
36
+ end
37
+
38
+ # Provides the currency_exchange_rate resource as a hash of all its readable attributes
39
+ def to_h
40
+ @object
41
+ end
42
+ end
43
+ end
44
+ end
@@ -23,11 +23,9 @@ module GoCardlessPro
23
23
  # way, it is no longer visible using this API.
24
24
  #
25
25
  # <p class="restricted-notice"><strong>Restricted</strong>: This API is
26
- # currently
27
- # only available for approved integrators - please <a
28
- # href="mailto:help@gocardless.com">get
29
- # in touch</a> if you would like to use this API.</p>
30
- #
26
+ # currently only available for approved integrators - please <a
27
+ # href="mailto:help@gocardless.com">get in touch</a> if you would like to
28
+ # use this API.</p>
31
29
  class CustomerNotification
32
30
  attr_reader :action_taken
33
31
  attr_reader :action_taken_at
@@ -14,7 +14,8 @@ module GoCardlessPro
14
14
 
15
15
  # Events are stored for all webhooks. An event refers to a resource which
16
16
  # has been updated, for example a payment which has been collected, or a
17
- # mandate which has been transferred.
17
+ # mandate which has been transferred. See [here](#event-actions) for a
18
+ # complete list of event types.
18
19
  class Event
19
20
  attr_reader :action
20
21
  attr_reader :created_at
@@ -47,16 +47,13 @@ module GoCardlessPro
47
47
  # system](#mandate-import-entries-list-all-mandate-import-entries).
48
48
  #
49
49
  # <p class="notice">Note that all Mandate Imports have an upper limit of
50
- # 30,000 entries, so
51
- # we recommend you split your import into several smaller imports if you're
52
- # planning to
53
- # exceed this threshold.</p>
50
+ # 30,000 entries, so we recommend you split your import into several smaller
51
+ # imports if you're planning to exceed this threshold.</p>
54
52
  #
55
53
  # <p class="restricted-notice"><strong>Restricted</strong>: This API is
56
- # currently
57
- # only available for approved integrators - please <a
58
- # href="mailto:help@gocardless.com">get
59
- # in touch</a> if you would like to use this API.</p>
54
+ # currently only available for approved integrators - please <a
55
+ # href="mailto:help@gocardless.com">get in touch</a> if you would like to
56
+ # use this API.</p>
60
57
  class MandateImport
61
58
  attr_reader :created_at
62
59
  attr_reader :id
@@ -39,11 +39,9 @@ module GoCardlessPro
39
39
  # been imported.
40
40
  #
41
41
  # <p class="restricted-notice"><strong>Restricted</strong>: This API is
42
- # currently
43
- # only available for approved integrators - please <a
44
- # href="mailto:help@gocardless.com">get
45
- # in touch</a> if you would like to use this API.</p>
46
- #
42
+ # currently only available for approved integrators - please <a
43
+ # href="mailto:help@gocardless.com">get in touch</a> if you would like to
44
+ # use this API.</p>
47
45
  class MandateImportEntry
48
46
  attr_reader :created_at
49
47
  attr_reader :record_identifier
@@ -26,6 +26,7 @@ module GoCardlessPro
26
26
  attr_reader :deducted_fees
27
27
  attr_reader :fx
28
28
  attr_reader :id
29
+ attr_reader :metadata
29
30
  attr_reader :payout_type
30
31
  attr_reader :reference
31
32
  attr_reader :status
@@ -43,6 +44,7 @@ module GoCardlessPro
43
44
  @fx = object['fx']
44
45
  @id = object['id']
45
46
  @links = object['links']
47
+ @metadata = object['metadata']
46
48
  @payout_type = object['payout_type']
47
49
  @reference = object['reference']
48
50
  @status = object['status']
@@ -49,6 +49,7 @@ module GoCardlessPro
49
49
  attr_reader :created_at
50
50
  attr_reader :description
51
51
  attr_reader :id
52
+ attr_reader :metadata
52
53
  attr_reader :redirect_url
53
54
  attr_reader :scheme
54
55
  attr_reader :session_token
@@ -64,6 +65,7 @@ module GoCardlessPro
64
65
  @description = object['description']
65
66
  @id = object['id']
66
67
  @links = object['links']
68
+ @metadata = object['metadata']
67
69
  @redirect_url = object['redirect_url']
68
70
  @scheme = object['scheme']
69
71
  @session_token = object['session_token']
@@ -20,40 +20,45 @@ module GoCardlessPro
20
20
  # The following rules apply when specifying recurrence:
21
21
  #
22
22
  # - The first payment must be charged within 1 year.
23
- # - When neither `month` nor `day_of_month` are present, the subscription
24
- # will recur from the `start_date` based on the `interval_unit`.
25
- # - If `month` or `day_of_month` are present, the recurrence rules will be
26
- # applied from the `start_date`, and the following validations apply:
23
+ # - If `day_of_month` and `start_date` are not provided `start_date` will be
24
+ # the [mandate](#core-endpoints-mandates)'s `next_possible_charge_date` and
25
+ # the subscription will then recur based on the `interval` & `interval_unit`
26
+ # - If `month` or `day_of_month` are present the following validations
27
+ # apply:
27
28
  #
28
- # | interval_unit | month |
29
- # day_of_month |
30
- # | :-------------- | :--------------------------------------------- |
31
- # :-------------------------------------- |
32
- # | yearly | optional (required if `day_of_month` provided) |
33
- # optional (required if `month` provided) |
34
- # | monthly | invalid |
35
- # required |
36
- # | weekly | invalid |
37
- # invalid |
29
+ # | __interval_unit__ | __month__ |
30
+ # __day_of_month__ |
31
+ # | :---------------- | :--------------------------------------------- |
32
+ # :----------------------------------------- |
33
+ # | yearly | optional (required if `day_of_month` provided) |
34
+ # optional (invalid if `month` not provided) |
35
+ # | monthly | invalid |
36
+ # optional |
37
+ # | weekly | invalid |
38
+ # invalid |
38
39
  #
39
40
  # Examples:
40
41
  #
41
- # | interval_unit | interval | month | day_of_month | valid?
42
- # |
43
- # | :-------------- | :--------- | :------ | :------------- |
42
+ # | __interval_unit__ | __interval__ | __month__ | __day_of_month__ | valid?
43
+ # |
44
+ # | :---------------- | :----------- | :-------- | :--------------- |
44
45
  # :------------------------------------------------- |
45
- # | yearly | 1 | january | -1 | valid
46
- # |
47
- # | yearly | 1 | march | | invalid -
48
- # missing `day_of_month` |
49
- # | monthly | 6 | | 12 | valid
50
- # |
51
- # | monthly | 6 | august | 12 | invalid -
52
- # `month` must be blank |
53
- # | weekly | 2 | | | valid
54
- # |
55
- # | weekly | 2 | october | 10 | invalid -
56
- # `month` and `day_of_month` must be blank |
46
+ # | yearly | 1 | january | -1 | valid
47
+ # |
48
+ # | monthly | 6 | | | valid
49
+ # |
50
+ # | monthly | 6 | | 12 | valid
51
+ # |
52
+ # | weekly | 2 | | | valid
53
+ # |
54
+ # | yearly | 1 | march | |
55
+ # invalid - missing `day_of_month` |
56
+ # | yearly | 1 | | 2 |
57
+ # invalid - missing `month` |
58
+ # | monthly | 6 | august | 12 |
59
+ # invalid - `month` must be blank |
60
+ # | weekly | 2 | october | 10 |
61
+ # invalid - `month` and `day_of_month` must be blank |
57
62
  #
58
63
  # ### Rolling dates
59
64
  #
@@ -69,9 +74,11 @@ module GoCardlessPro
69
74
  class Subscription
70
75
  attr_reader :amount
71
76
  attr_reader :app_fee
77
+ attr_reader :count
72
78
  attr_reader :created_at
73
79
  attr_reader :currency
74
80
  attr_reader :day_of_month
81
+ attr_reader :earliest_charge_date_after_resume
75
82
  attr_reader :end_date
76
83
  attr_reader :id
77
84
  attr_reader :interval
@@ -92,9 +99,11 @@ module GoCardlessPro
92
99
 
93
100
  @amount = object['amount']
94
101
  @app_fee = object['app_fee']
102
+ @count = object['count']
95
103
  @created_at = object['created_at']
96
104
  @currency = object['currency']
97
105
  @day_of_month = object['day_of_month']
106
+ @earliest_charge_date_after_resume = object['earliest_charge_date_after_resume']
98
107
  @end_date = object['end_date']
99
108
  @id = object['id']
100
109
  @interval = object['interval']
@@ -0,0 +1,67 @@
1
+ require_relative './base_service'
2
+ require 'uri'
3
+
4
+ # encoding: utf-8
5
+ #
6
+ # This client is automatically generated from a template and JSON schema definition.
7
+ # See https://github.com/gocardless/gocardless-pro-ruby#contributing before editing.
8
+ #
9
+
10
+ module GoCardlessPro
11
+ module Services
12
+ # Service for making requests to the CurrencyExchangeRate endpoints
13
+ class CurrencyExchangeRatesService < BaseService
14
+ # Returns a [cursor-paginated](#api-usage-cursor-pagination) list of all
15
+ # exchange rates.
16
+ # Example URL: /currency_exchange_rates
17
+ # @param options [Hash] parameters as a hash, under a params key.
18
+ def list(options = {})
19
+ path = '/currency_exchange_rates'
20
+
21
+ options[:retry_failures] = true
22
+
23
+ response = make_request(:get, path, options)
24
+
25
+ ListResponse.new(
26
+ response: response,
27
+ unenveloped_body: unenvelope_body(response.body),
28
+ resource_class: Resources::CurrencyExchangeRate
29
+ )
30
+ end
31
+
32
+ # Get a lazily enumerated list of all the items returned. This is simmilar to the `list` method but will paginate for you automatically.
33
+ #
34
+ # @param options [Hash] parameters as a hash. If the request is a GET, these will be converted to query parameters.
35
+ # Otherwise they will be the body of the request.
36
+ def all(options = {})
37
+ Paginator.new(
38
+ service: self,
39
+ options: options
40
+ ).enumerator
41
+ end
42
+
43
+ private
44
+
45
+ # Unenvelope the response of the body using the service's `envelope_key`
46
+ #
47
+ # @param body [Hash]
48
+ def unenvelope_body(body)
49
+ body[envelope_key] || body['data']
50
+ end
51
+
52
+ # return the key which API responses will envelope data under
53
+ def envelope_key
54
+ 'currency_exchange_rates'
55
+ end
56
+
57
+ # take a URL with placeholder params and substitute them out for the actual value
58
+ # @param url [String] the URL with placeholders in
59
+ # @param param_map [Hash] a hash of placeholders and their actual values (which will be escaped)
60
+ def sub_url(url, param_map)
61
+ param_map.reduce(url) do |new_url, (param, value)|
62
+ new_url.gsub(":#{param}", URI.escape(value))
63
+ end
64
+ end
65
+ end
66
+ end
67
+ end
@@ -123,8 +123,7 @@ module GoCardlessPro
123
123
  # ID.
124
124
  #
125
125
  # <p class="restricted-notice"><strong>The action of removing a customer cannot
126
- # be
127
- # reversed, so please use with care.</strong></p>
126
+ # be reversed, so please use with care.</strong></p>
128
127
  # Example URL: /customers/:identity
129
128
  #
130
129
  # @param identity # Unique identifier, beginning with "CU".
@@ -12,11 +12,66 @@ module GoCardlessPro
12
12
  # Service for making requests to the InstalmentSchedule endpoints
13
13
  class InstalmentSchedulesService < BaseService
14
14
  # Creates a new instalment schedule object, along with the associated payments.
15
+ # This
16
+ # API is recommended if you know the specific dates you wish to charge.
17
+ # Otherwise,
18
+ # please check out the [scheduling
19
+ # version](#instalment-schedules-create-with-schedule).
15
20
  #
16
- # The `instalments` property can either be an array of payment properties
17
- # (`amount`
18
- # and `charge_date`) or a schedule object with `interval`, `interval_unit` and
19
- # `amounts`.
21
+ # The `instalments` property is an array of payment properties (`amount` and
22
+ # `charge_date`).
23
+ #
24
+ # It can take quite a while to create the associated payments, so the API will
25
+ # return
26
+ # the status as `pending` initially. When processing has completed, a subsequent
27
+ # GET
28
+ # request for the instalment schedule will either have the status `success` and
29
+ # link
30
+ # to the created payments, or the status `error` and detailed information about
31
+ # the
32
+ # failures.
33
+ # Example URL: /instalment_schedules
34
+ # @param options [Hash] parameters as a hash, under a params key.
35
+ def create_with_dates(options = {})
36
+ path = '/instalment_schedules'
37
+
38
+ params = options.delete(:params) || {}
39
+ options[:params] = {}
40
+ options[:params][envelope_key] = params
41
+
42
+ options[:retry_failures] = true
43
+
44
+ begin
45
+ response = make_request(:post, path, options)
46
+
47
+ # Response doesn't raise any errors until #body is called
48
+ response.tap(&:body)
49
+ rescue InvalidStateError => e
50
+ if e.idempotent_creation_conflict?
51
+ case @api_service.on_idempotency_conflict
52
+ when :raise
53
+ raise IdempotencyConflict, e.error
54
+ when :fetch
55
+ return get(e.conflicting_resource_id)
56
+ else
57
+ raise ArgumentError, 'Unknown mode for :on_idempotency_conflict'
58
+ end
59
+ end
60
+
61
+ raise e
62
+ end
63
+
64
+ return if response.body.nil?
65
+
66
+ Resources::InstalmentSchedule.new(unenvelope_body(response.body), response)
67
+ end
68
+
69
+ # Creates a new instalment schedule object, along with the associated payments.
70
+ # This
71
+ # API is recommended if you wish to use the GoCardless scheduling logic. For
72
+ # finer
73
+ # control over the individual dates, please check out the [alternative
74
+ # version](#instalment-schedules-create-with-dates).
20
75
  #
21
76
  # It can take quite a while to create the associated payments, so the API will
22
77
  # return
@@ -27,7 +82,7 @@ module GoCardlessPro
27
82
  # failures.
28
83
  # Example URL: /instalment_schedules
29
84
  # @param options [Hash] parameters as a hash, under a params key.
30
- def create(options = {})
85
+ def create_with_schedule(options = {})
31
86
  path = '/instalment_schedules'
32
87
 
33
88
  params = options.delete(:params) || {}
@@ -107,6 +162,27 @@ module GoCardlessPro
107
162
  Resources::InstalmentSchedule.new(unenvelope_body(response.body), response)
108
163
  end
109
164
 
165
+ # Updates an instalment schedule. This accepts only the metadata parameter.
166
+ # Example URL: /instalment_schedules/:identity
167
+ #
168
+ # @param identity # Unique identifier, beginning with "IS".
169
+ # @param options [Hash] parameters as a hash, under a params key.
170
+ def update(identity, options = {})
171
+ path = sub_url('/instalment_schedules/:identity', 'identity' => identity)
172
+
173
+ params = options.delete(:params) || {}
174
+ options[:params] = {}
175
+ options[:params][envelope_key] = params
176
+
177
+ options[:retry_failures] = true
178
+
179
+ response = make_request(:put, path, options)
180
+
181
+ return if response.body.nil?
182
+
183
+ Resources::InstalmentSchedule.new(unenvelope_body(response.body), response)
184
+ end
185
+
110
186
  # Immediately cancels an instalment schedule; no further payments will be
111
187
  # collected for it.
112
188
  #