gocardless_pro 2.24.0 → 2.29.0

Sign up to get free protection for your applications and to get access to all the features.
Files changed (82) hide show
  1. checksums.yaml +4 -4
  2. data/.circleci/config.yml +23 -4
  3. data/lib/gocardless_pro/api_service.rb +4 -0
  4. data/lib/gocardless_pro/client.rb +46 -1
  5. data/lib/gocardless_pro/error/authentication_error.rb +4 -0
  6. data/lib/gocardless_pro/error/permission_error.rb +4 -0
  7. data/lib/gocardless_pro/error/rate_limit_error.rb +4 -0
  8. data/lib/gocardless_pro/middlewares/raise_gocardless_errors.rb +12 -1
  9. data/lib/gocardless_pro/resources/bank_authorisation.rb +81 -0
  10. data/lib/gocardless_pro/resources/billing_request.rb +108 -0
  11. data/lib/gocardless_pro/resources/billing_request_flow.rb +72 -0
  12. data/lib/gocardless_pro/resources/billing_request_template.rb +68 -0
  13. data/lib/gocardless_pro/resources/block.rb +66 -0
  14. data/lib/gocardless_pro/resources/creditor.rb +2 -3
  15. data/lib/gocardless_pro/resources/event.rb +20 -0
  16. data/lib/gocardless_pro/resources/institution.rb +47 -0
  17. data/lib/gocardless_pro/resources/payer_authorisation.rb +131 -0
  18. data/lib/gocardless_pro/resources/payout_item.rb +4 -0
  19. data/lib/gocardless_pro/resources/redirect_flow.rb +2 -0
  20. data/lib/gocardless_pro/resources/scenario_simulator.rb +42 -0
  21. data/lib/gocardless_pro/resources/webhook.rb +62 -0
  22. data/lib/gocardless_pro/services/bank_authorisations_service.rb +80 -0
  23. data/lib/gocardless_pro/services/billing_request_flows_service.rb +70 -0
  24. data/lib/gocardless_pro/services/billing_request_templates_service.rb +131 -0
  25. data/lib/gocardless_pro/services/billing_requests_service.rb +352 -0
  26. data/lib/gocardless_pro/services/blocks_service.rb +223 -0
  27. data/lib/gocardless_pro/services/creditor_bank_accounts_service.rb +1 -5
  28. data/lib/gocardless_pro/services/creditors_service.rb +1 -3
  29. data/lib/gocardless_pro/services/currency_exchange_rates_service.rb +1 -1
  30. data/lib/gocardless_pro/services/customer_bank_accounts_service.rb +1 -5
  31. data/lib/gocardless_pro/services/customers_service.rb +1 -3
  32. data/lib/gocardless_pro/services/events_service.rb +1 -1
  33. data/lib/gocardless_pro/services/instalment_schedules_service.rb +1 -7
  34. data/lib/gocardless_pro/services/institutions_service.rb +56 -0
  35. data/lib/gocardless_pro/services/mandate_import_entries_service.rb +1 -1
  36. data/lib/gocardless_pro/services/mandate_imports_service.rb +0 -6
  37. data/lib/gocardless_pro/services/mandates_service.rb +1 -7
  38. data/lib/gocardless_pro/services/payer_authorisations_service.rb +202 -0
  39. data/lib/gocardless_pro/services/payments_service.rb +1 -7
  40. data/lib/gocardless_pro/services/payout_items_service.rb +1 -1
  41. data/lib/gocardless_pro/services/payouts_service.rb +1 -1
  42. data/lib/gocardless_pro/services/redirect_flows_service.rb +0 -4
  43. data/lib/gocardless_pro/services/refunds_service.rb +1 -3
  44. data/lib/gocardless_pro/services/scenario_simulators_service.rb +170 -0
  45. data/lib/gocardless_pro/services/subscriptions_service.rb +10 -13
  46. data/lib/gocardless_pro/services/tax_rates_service.rb +1 -1
  47. data/lib/gocardless_pro/services/webhooks_service.rb +111 -0
  48. data/lib/gocardless_pro/version.rb +1 -1
  49. data/lib/gocardless_pro.rb +30 -0
  50. data/spec/api_service_spec.rb +12 -1
  51. data/spec/middlewares/raise_gocardless_errors_spec.rb +30 -0
  52. data/spec/resources/bank_authorisation_spec.rb +259 -0
  53. data/spec/resources/billing_request_flow_spec.rb +219 -0
  54. data/spec/resources/billing_request_spec.rb +782 -0
  55. data/spec/resources/billing_request_template_spec.rb +502 -0
  56. data/spec/resources/block_spec.rb +560 -0
  57. data/spec/resources/institution_spec.rb +108 -0
  58. data/spec/resources/payer_authorisation_spec.rb +418 -0
  59. data/spec/resources/redirect_flow_spec.rb +9 -0
  60. data/spec/resources/scenario_simulator_spec.rb +63 -0
  61. data/spec/resources/webhook_spec.rb +323 -0
  62. data/spec/services/bank_authorisations_service_spec.rb +353 -0
  63. data/spec/services/billing_request_flows_service_spec.rb +253 -0
  64. data/spec/services/billing_request_templates_service_spec.rb +789 -0
  65. data/spec/services/billing_requests_service_spec.rb +1082 -0
  66. data/spec/services/blocks_service_spec.rb +823 -0
  67. data/spec/services/creditor_bank_accounts_service_spec.rb +0 -13
  68. data/spec/services/creditors_service_spec.rb +0 -13
  69. data/spec/services/customer_bank_accounts_service_spec.rb +0 -13
  70. data/spec/services/customers_service_spec.rb +0 -13
  71. data/spec/services/instalment_schedules_service_spec.rb +0 -26
  72. data/spec/services/institutions_service_spec.rb +232 -0
  73. data/spec/services/mandate_imports_service_spec.rb +0 -13
  74. data/spec/services/mandates_service_spec.rb +0 -13
  75. data/spec/services/payer_authorisations_service_spec.rb +559 -0
  76. data/spec/services/payments_service_spec.rb +0 -13
  77. data/spec/services/redirect_flows_service_spec.rb +9 -13
  78. data/spec/services/refunds_service_spec.rb +0 -13
  79. data/spec/services/scenario_simulators_service_spec.rb +74 -0
  80. data/spec/services/subscriptions_service_spec.rb +0 -13
  81. data/spec/services/webhooks_service_spec.rb +545 -0
  82. metadata +64 -7
@@ -212,19 +212,6 @@ describe GoCardlessPro::Services::CreditorBankAccountsService do
212
212
  to raise_error(GoCardlessPro::IdempotencyConflict)
213
213
  end
214
214
  end
215
-
216
- context 'with on_idempotency_conflict: :unknown' do
217
- let(:client) do
218
- GoCardlessPro::Client.new(
219
- access_token: 'SECRET_TOKEN',
220
- on_idempotency_conflict: :unknown
221
- )
222
- end
223
-
224
- it 'raises an ArgumentError' do
225
- expect { post_create_response }.to raise_error(ArgumentError)
226
- end
227
- end
228
215
  end
229
216
  end
230
217
 
@@ -252,19 +252,6 @@ describe GoCardlessPro::Services::CreditorsService do
252
252
  to raise_error(GoCardlessPro::IdempotencyConflict)
253
253
  end
254
254
  end
255
-
256
- context 'with on_idempotency_conflict: :unknown' do
257
- let(:client) do
258
- GoCardlessPro::Client.new(
259
- access_token: 'SECRET_TOKEN',
260
- on_idempotency_conflict: :unknown
261
- )
262
- end
263
-
264
- it 'raises an ArgumentError' do
265
- expect { post_create_response }.to raise_error(ArgumentError)
266
- end
267
- end
268
255
  end
269
256
  end
270
257
 
@@ -212,19 +212,6 @@ describe GoCardlessPro::Services::CustomerBankAccountsService do
212
212
  to raise_error(GoCardlessPro::IdempotencyConflict)
213
213
  end
214
214
  end
215
-
216
- context 'with on_idempotency_conflict: :unknown' do
217
- let(:client) do
218
- GoCardlessPro::Client.new(
219
- access_token: 'SECRET_TOKEN',
220
- on_idempotency_conflict: :unknown
221
- )
222
- end
223
-
224
- it 'raises an ArgumentError' do
225
- expect { post_create_response }.to raise_error(ArgumentError)
226
- end
227
- end
228
215
  end
229
216
  end
230
217
 
@@ -247,19 +247,6 @@ describe GoCardlessPro::Services::CustomersService do
247
247
  to raise_error(GoCardlessPro::IdempotencyConflict)
248
248
  end
249
249
  end
250
-
251
- context 'with on_idempotency_conflict: :unknown' do
252
- let(:client) do
253
- GoCardlessPro::Client.new(
254
- access_token: 'SECRET_TOKEN',
255
- on_idempotency_conflict: :unknown
256
- )
257
- end
258
-
259
- it 'raises an ArgumentError' do
260
- expect { post_create_response }.to raise_error(ArgumentError)
261
- end
262
- end
263
250
  end
264
251
  end
265
252
 
@@ -202,19 +202,6 @@ describe GoCardlessPro::Services::InstalmentSchedulesService do
202
202
  to raise_error(GoCardlessPro::IdempotencyConflict)
203
203
  end
204
204
  end
205
-
206
- context 'with on_idempotency_conflict: :unknown' do
207
- let(:client) do
208
- GoCardlessPro::Client.new(
209
- access_token: 'SECRET_TOKEN',
210
- on_idempotency_conflict: :unknown
211
- )
212
- end
213
-
214
- it 'raises an ArgumentError' do
215
- expect { post_create_response }.to raise_error(ArgumentError)
216
- end
217
- end
218
205
  end
219
206
  end
220
207
 
@@ -411,19 +398,6 @@ describe GoCardlessPro::Services::InstalmentSchedulesService do
411
398
  to raise_error(GoCardlessPro::IdempotencyConflict)
412
399
  end
413
400
  end
414
-
415
- context 'with on_idempotency_conflict: :unknown' do
416
- let(:client) do
417
- GoCardlessPro::Client.new(
418
- access_token: 'SECRET_TOKEN',
419
- on_idempotency_conflict: :unknown
420
- )
421
- end
422
-
423
- it 'raises an ArgumentError' do
424
- expect { post_create_response }.to raise_error(ArgumentError)
425
- end
426
- end
427
401
  end
428
402
  end
429
403
 
@@ -0,0 +1,232 @@
1
+ require 'spec_helper'
2
+
3
+ describe GoCardlessPro::Services::InstitutionsService do
4
+ let(:client) do
5
+ GoCardlessPro::Client.new(
6
+ access_token: 'SECRET_TOKEN'
7
+ )
8
+ end
9
+
10
+ let(:response_headers) { { 'Content-Type' => 'application/json' } }
11
+
12
+ describe '#list' do
13
+ describe 'with no filters' do
14
+ subject(:get_list_response) { client.institutions.list }
15
+
16
+ let(:body) do
17
+ {
18
+ 'institutions' => [{
19
+
20
+ 'country_code' => 'country_code-input',
21
+ 'icon_url' => 'icon_url-input',
22
+ 'id' => 'id-input',
23
+ 'logo_url' => 'logo_url-input',
24
+ 'name' => 'name-input',
25
+ }],
26
+ meta: {
27
+ cursors: {
28
+ before: nil,
29
+ after: 'ABC123',
30
+ },
31
+ },
32
+ }.to_json
33
+ end
34
+
35
+ before do
36
+ stub_request(:get, %r{.*api.gocardless.com/institutions}).to_return(
37
+ body: body,
38
+ headers: response_headers
39
+ )
40
+ end
41
+
42
+ it 'wraps each item in the resource class' do
43
+ expect(get_list_response.records.map(&:class).uniq.first).to eq(GoCardlessPro::Resources::Institution)
44
+
45
+ expect(get_list_response.records.first.country_code).to eq('country_code-input')
46
+
47
+ expect(get_list_response.records.first.icon_url).to eq('icon_url-input')
48
+
49
+ expect(get_list_response.records.first.id).to eq('id-input')
50
+
51
+ expect(get_list_response.records.first.logo_url).to eq('logo_url-input')
52
+
53
+ expect(get_list_response.records.first.name).to eq('name-input')
54
+ end
55
+
56
+ it 'exposes the cursors for before and after' do
57
+ expect(get_list_response.before).to eq(nil)
58
+ expect(get_list_response.after).to eq('ABC123')
59
+ end
60
+
61
+ specify { expect(get_list_response.api_response.headers).to eql('content-type' => 'application/json') }
62
+
63
+ describe 'retry behaviour' do
64
+ before { allow_any_instance_of(GoCardlessPro::Request).to receive(:sleep) }
65
+
66
+ it 'retries timeouts' do
67
+ stub = stub_request(:get, %r{.*api.gocardless.com/institutions}).
68
+ to_timeout.then.to_return(status: 200, headers: response_headers, body: body)
69
+
70
+ get_list_response
71
+ expect(stub).to have_been_requested.twice
72
+ end
73
+
74
+ it 'retries 5XX errors' do
75
+ stub = stub_request(:get, %r{.*api.gocardless.com/institutions}).
76
+ to_return(status: 502,
77
+ headers: { 'Content-Type' => 'text/html' },
78
+ body: '<html><body>Response from Cloudflare</body></html>').
79
+ then.to_return(status: 200, headers: response_headers, body: body)
80
+
81
+ get_list_response
82
+ expect(stub).to have_been_requested.twice
83
+ end
84
+ end
85
+ end
86
+ end
87
+
88
+ describe '#all' do
89
+ let!(:first_response_stub) do
90
+ stub_request(:get, %r{.*api.gocardless.com/institutions$}).to_return(
91
+ body: {
92
+ 'institutions' => [{
93
+
94
+ 'country_code' => 'country_code-input',
95
+ 'icon_url' => 'icon_url-input',
96
+ 'id' => 'id-input',
97
+ 'logo_url' => 'logo_url-input',
98
+ 'name' => 'name-input',
99
+ }],
100
+ meta: {
101
+ cursors: { after: 'AB345' },
102
+ limit: 1,
103
+ },
104
+ }.to_json,
105
+ headers: response_headers
106
+ )
107
+ end
108
+
109
+ let!(:second_response_stub) do
110
+ stub_request(:get, %r{.*api.gocardless.com/institutions\?after=AB345}).to_return(
111
+ body: {
112
+ 'institutions' => [{
113
+
114
+ 'country_code' => 'country_code-input',
115
+ 'icon_url' => 'icon_url-input',
116
+ 'id' => 'id-input',
117
+ 'logo_url' => 'logo_url-input',
118
+ 'name' => 'name-input',
119
+ }],
120
+ meta: {
121
+ limit: 2,
122
+ cursors: {},
123
+ },
124
+ }.to_json,
125
+ headers: response_headers
126
+ )
127
+ end
128
+
129
+ it 'automatically makes the extra requests' do
130
+ expect(client.institutions.all.to_a.length).to eq(2)
131
+ expect(first_response_stub).to have_been_requested
132
+ expect(second_response_stub).to have_been_requested
133
+ end
134
+
135
+ describe 'retry behaviour' do
136
+ before { allow_any_instance_of(GoCardlessPro::Request).to receive(:sleep) }
137
+
138
+ it 'retries timeouts' do
139
+ first_response_stub = stub_request(:get, %r{.*api.gocardless.com/institutions$}).to_return(
140
+ body: {
141
+ 'institutions' => [{
142
+
143
+ 'country_code' => 'country_code-input',
144
+ 'icon_url' => 'icon_url-input',
145
+ 'id' => 'id-input',
146
+ 'logo_url' => 'logo_url-input',
147
+ 'name' => 'name-input',
148
+ }],
149
+ meta: {
150
+ cursors: { after: 'AB345' },
151
+ limit: 1,
152
+ },
153
+ }.to_json,
154
+ headers: response_headers
155
+ )
156
+
157
+ second_response_stub = stub_request(:get, %r{.*api.gocardless.com/institutions\?after=AB345}).
158
+ to_timeout.then.
159
+ to_return(
160
+ body: {
161
+ 'institutions' => [{
162
+
163
+ 'country_code' => 'country_code-input',
164
+ 'icon_url' => 'icon_url-input',
165
+ 'id' => 'id-input',
166
+ 'logo_url' => 'logo_url-input',
167
+ 'name' => 'name-input',
168
+ }],
169
+ meta: {
170
+ limit: 2,
171
+ cursors: {},
172
+ },
173
+ }.to_json,
174
+ headers: response_headers
175
+ )
176
+
177
+ client.institutions.all.to_a
178
+
179
+ expect(first_response_stub).to have_been_requested
180
+ expect(second_response_stub).to have_been_requested.twice
181
+ end
182
+
183
+ it 'retries 5XX errors' do
184
+ first_response_stub = stub_request(:get, %r{.*api.gocardless.com/institutions$}).to_return(
185
+ body: {
186
+ 'institutions' => [{
187
+
188
+ 'country_code' => 'country_code-input',
189
+ 'icon_url' => 'icon_url-input',
190
+ 'id' => 'id-input',
191
+ 'logo_url' => 'logo_url-input',
192
+ 'name' => 'name-input',
193
+ }],
194
+ meta: {
195
+ cursors: { after: 'AB345' },
196
+ limit: 1,
197
+ },
198
+ }.to_json,
199
+ headers: response_headers
200
+ )
201
+
202
+ second_response_stub = stub_request(:get, %r{.*api.gocardless.com/institutions\?after=AB345}).
203
+ to_return(
204
+ status: 502,
205
+ body: '<html><body>Response from Cloudflare</body></html>',
206
+ headers: { 'Content-Type' => 'text/html' }
207
+ ).then.to_return(
208
+ body: {
209
+ 'institutions' => [{
210
+
211
+ 'country_code' => 'country_code-input',
212
+ 'icon_url' => 'icon_url-input',
213
+ 'id' => 'id-input',
214
+ 'logo_url' => 'logo_url-input',
215
+ 'name' => 'name-input',
216
+ }],
217
+ meta: {
218
+ limit: 2,
219
+ cursors: {},
220
+ },
221
+ }.to_json,
222
+ headers: response_headers
223
+ )
224
+
225
+ client.institutions.all.to_a
226
+
227
+ expect(first_response_stub).to have_been_requested
228
+ expect(second_response_stub).to have_been_requested.twice
229
+ end
230
+ end
231
+ end
232
+ end
@@ -177,19 +177,6 @@ describe GoCardlessPro::Services::MandateImportsService do
177
177
  to raise_error(GoCardlessPro::IdempotencyConflict)
178
178
  end
179
179
  end
180
-
181
- context 'with on_idempotency_conflict: :unknown' do
182
- let(:client) do
183
- GoCardlessPro::Client.new(
184
- access_token: 'SECRET_TOKEN',
185
- on_idempotency_conflict: :unknown
186
- )
187
- end
188
-
189
- it 'raises an ArgumentError' do
190
- expect { post_create_response }.to raise_error(ArgumentError)
191
- end
192
- end
193
180
  end
194
181
  end
195
182
 
@@ -202,19 +202,6 @@ describe GoCardlessPro::Services::MandatesService do
202
202
  to raise_error(GoCardlessPro::IdempotencyConflict)
203
203
  end
204
204
  end
205
-
206
- context 'with on_idempotency_conflict: :unknown' do
207
- let(:client) do
208
- GoCardlessPro::Client.new(
209
- access_token: 'SECRET_TOKEN',
210
- on_idempotency_conflict: :unknown
211
- )
212
- end
213
-
214
- it 'raises an ArgumentError' do
215
- expect { post_create_response }.to raise_error(ArgumentError)
216
- end
217
- end
218
205
  end
219
206
  end
220
207