stripe-ruby-mock 2.5.3 → 2.5.4
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +4 -4
- data/README.md +3 -2
- data/lib/stripe_mock.rb +5 -0
- data/lib/stripe_mock/data.rb +15 -15
- data/lib/stripe_mock/instance.rb +1 -0
- data/lib/stripe_mock/request_handlers/charges.rb +1 -1
- data/lib/stripe_mock/request_handlers/customers.rb +1 -1
- data/lib/stripe_mock/request_handlers/external_accounts.rb +55 -0
- data/lib/stripe_mock/request_handlers/helpers/bank_account_helpers.rb +1 -1
- data/lib/stripe_mock/request_handlers/helpers/card_helpers.rb +5 -5
- data/lib/stripe_mock/request_handlers/helpers/external_account_helpers.rb +49 -0
- data/lib/stripe_mock/request_handlers/helpers/subscription_helpers.rb +14 -13
- data/lib/stripe_mock/request_handlers/invoices.rb +3 -3
- data/lib/stripe_mock/request_handlers/plans.rb +1 -0
- data/lib/stripe_mock/request_handlers/subscriptions.rb +35 -54
- data/lib/stripe_mock/test_strategies/base.rb +3 -3
- data/lib/stripe_mock/version.rb +1 -1
- data/spec/instance_spec.rb +14 -0
- data/spec/shared_stripe_examples/bank_examples.rb +1 -1
- data/spec/shared_stripe_examples/charge_examples.rb +1 -1
- data/spec/shared_stripe_examples/customer_examples.rb +2 -2
- data/spec/shared_stripe_examples/external_account_examples.rb +170 -0
- data/spec/shared_stripe_examples/invoice_examples.rb +15 -14
- data/spec/shared_stripe_examples/plan_examples.rb +11 -0
- data/spec/shared_stripe_examples/subscription_examples.rb +69 -5
- data/spec/support/stripe_examples.rb +1 -0
- metadata +6 -3
- data/ChangeLog.rdoc +0 -4
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA1:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: 771c4e4adbc92b37176d94b8f91fb1f2bef740ba
|
4
|
+
data.tar.gz: 86c21735586588ea3aabc958d3eb93dda6dbc7ec
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: 0c747fed9cf7824d59fdb1be3ec1b399beabd69d54d08101c1c46d96792fe400e4d7b8c1aa6a816c981d58d902a3fdf46c6edff21bd280a07615799384a4a82f
|
7
|
+
data.tar.gz: 68b2ab17e0f504f783bd8c5a20893ec89bee491a29cac16a824d8cdb45e48f7a2a34e307b153feb7fe58662ee661d2732c4d838391cf23497ea20fe0a90393a5
|
data/README.md
CHANGED
@@ -12,7 +12,7 @@ This gem has unexpectedly grown in popularity and I've gotten pretty busy, so I'
|
|
12
12
|
|
13
13
|
In your gemfile:
|
14
14
|
|
15
|
-
gem 'stripe-ruby-mock', '~> 2.5.
|
15
|
+
gem 'stripe-ruby-mock', '~> 2.5.4', :require => 'stripe_mock'
|
16
16
|
|
17
17
|
## Features
|
18
18
|
|
@@ -68,7 +68,7 @@ describe MyApp do
|
|
68
68
|
# Specify :source in place of :card (with same value) to return customer with source data
|
69
69
|
customer = Stripe::Customer.create({
|
70
70
|
email: 'johnny@appleseed.com',
|
71
|
-
|
71
|
+
source: stripe_helper.generate_card_token
|
72
72
|
})
|
73
73
|
expect(customer.email).to eq('johnny@appleseed.com')
|
74
74
|
end
|
@@ -170,6 +170,7 @@ StripeMock.prepare_card_error(:incorrect_cvc)
|
|
170
170
|
StripeMock.prepare_card_error(:card_declined)
|
171
171
|
StripeMock.prepare_card_error(:missing)
|
172
172
|
StripeMock.prepare_card_error(:processing_error)
|
173
|
+
StripeMock.prepare_card_error(:incorrect_zip)
|
173
174
|
```
|
174
175
|
|
175
176
|
You can see the details of each error in [lib/stripe_mock/api/errors.rb](lib/stripe_mock/api/errors.rb)
|
data/lib/stripe_mock.rb
CHANGED
@@ -1,6 +1,7 @@
|
|
1
1
|
require 'ostruct'
|
2
2
|
require 'multi_json'
|
3
3
|
require 'dante'
|
4
|
+
require 'time'
|
4
5
|
|
5
6
|
require 'stripe'
|
6
7
|
|
@@ -37,6 +38,7 @@ require 'stripe_mock/api/test_helpers'
|
|
37
38
|
require 'stripe_mock/api/webhooks'
|
38
39
|
|
39
40
|
require 'stripe_mock/request_handlers/helpers/bank_account_helpers.rb'
|
41
|
+
require 'stripe_mock/request_handlers/helpers/external_account_helpers.rb'
|
40
42
|
require 'stripe_mock/request_handlers/helpers/card_helpers.rb'
|
41
43
|
require 'stripe_mock/request_handlers/helpers/charge_helpers.rb'
|
42
44
|
require 'stripe_mock/request_handlers/helpers/coupon_helpers.rb'
|
@@ -46,6 +48,7 @@ require 'stripe_mock/request_handlers/helpers/token_helpers.rb'
|
|
46
48
|
require 'stripe_mock/request_handlers/validators/param_validators.rb'
|
47
49
|
|
48
50
|
require 'stripe_mock/request_handlers/accounts.rb'
|
51
|
+
require 'stripe_mock/request_handlers/external_accounts.rb'
|
49
52
|
require 'stripe_mock/request_handlers/balance.rb'
|
50
53
|
require 'stripe_mock/request_handlers/balance_transactions.rb'
|
51
54
|
require 'stripe_mock/request_handlers/charges.rb'
|
@@ -74,11 +77,13 @@ require 'stripe_mock/test_strategies/live.rb'
|
|
74
77
|
|
75
78
|
module StripeMock
|
76
79
|
|
80
|
+
@default_currency = 'usd'
|
77
81
|
lib_dir = File.expand_path(File.dirname(__FILE__), '../..')
|
78
82
|
@webhook_fixture_path = './spec/fixtures/stripe_webhooks/'
|
79
83
|
@webhook_fixture_fallback_path = File.join(lib_dir, 'stripe_mock/webhook_fixtures')
|
80
84
|
|
81
85
|
class << self
|
86
|
+
attr_accessor :default_currency
|
82
87
|
attr_accessor :webhook_fixture_path
|
83
88
|
end
|
84
89
|
end
|
data/lib/stripe_mock/data.rb
CHANGED
@@ -3,7 +3,7 @@ module StripeMock
|
|
3
3
|
|
4
4
|
def self.mock_account(params = {})
|
5
5
|
id = params[:id] || 'acct_103ED82ePvKYlo2C'
|
6
|
-
currency = params[:currency] ||
|
6
|
+
currency = params[:currency] || StripeMock.default_currency
|
7
7
|
{
|
8
8
|
id: id,
|
9
9
|
email: "bob@example.com",
|
@@ -103,7 +103,7 @@ module StripeMock
|
|
103
103
|
|
104
104
|
def self.mock_customer(sources, params)
|
105
105
|
cus_id = params[:id] || "test_cus_default"
|
106
|
-
currency = params[:currency] ||
|
106
|
+
currency = params[:currency] || StripeMock.default_currency
|
107
107
|
sources.each {|source| source[:customer] = cus_id}
|
108
108
|
{
|
109
109
|
email: 'stripe_mock@example.com',
|
@@ -134,7 +134,7 @@ module StripeMock
|
|
134
134
|
|
135
135
|
def self.mock_charge(params={})
|
136
136
|
charge_id = params[:id] || "ch_1fD6uiR9FAA2zc"
|
137
|
-
currency = params[:currency] ||
|
137
|
+
currency = params[:currency] || StripeMock.default_currency
|
138
138
|
{
|
139
139
|
id: charge_id,
|
140
140
|
object: "charge",
|
@@ -196,7 +196,7 @@ module StripeMock
|
|
196
196
|
end
|
197
197
|
|
198
198
|
def self.mock_refund(params={})
|
199
|
-
currency = params[:currency] ||
|
199
|
+
currency = params[:currency] || StripeMock.default_currency
|
200
200
|
{
|
201
201
|
id: "re_4fWhgUh5si7InF",
|
202
202
|
amount: 1,
|
@@ -248,7 +248,7 @@ module StripeMock
|
|
248
248
|
end
|
249
249
|
|
250
250
|
def self.mock_bank_account(params={})
|
251
|
-
currency = params[:currency] ||
|
251
|
+
currency = params[:currency] || StripeMock.default_currency
|
252
252
|
{
|
253
253
|
id: "test_ba_default",
|
254
254
|
object: "bank_account",
|
@@ -306,7 +306,7 @@ module StripeMock
|
|
306
306
|
plan: {
|
307
307
|
amount: 999,
|
308
308
|
created: 1504035972,
|
309
|
-
currency:
|
309
|
+
currency: StripeMock.default_currency
|
310
310
|
},
|
311
311
|
quantity: 1
|
312
312
|
}]
|
@@ -328,7 +328,7 @@ module StripeMock
|
|
328
328
|
|
329
329
|
def self.mock_invoice(lines, params={})
|
330
330
|
in_id = params[:id] || "test_in_default"
|
331
|
-
currency = params[:currency] ||
|
331
|
+
currency = params[:currency] || StripeMock.default_currency
|
332
332
|
lines << Data.mock_line_item() if lines.empty?
|
333
333
|
invoice = {
|
334
334
|
id: 'in_test_invoice',
|
@@ -379,7 +379,7 @@ module StripeMock
|
|
379
379
|
end
|
380
380
|
|
381
381
|
def self.mock_line_item(params = {})
|
382
|
-
currency = params[:currency] ||
|
382
|
+
currency = params[:currency] || StripeMock.default_currency
|
383
383
|
{
|
384
384
|
id: "ii_test",
|
385
385
|
object: "line_item",
|
@@ -402,7 +402,7 @@ module StripeMock
|
|
402
402
|
end
|
403
403
|
|
404
404
|
def self.mock_invoice_item(params = {})
|
405
|
-
currency = params[:currency] ||
|
405
|
+
currency = params[:currency] || StripeMock.default_currency
|
406
406
|
{
|
407
407
|
id: "test_ii",
|
408
408
|
object: "invoiceitem",
|
@@ -490,7 +490,7 @@ module StripeMock
|
|
490
490
|
end
|
491
491
|
|
492
492
|
def self.mock_plan(params={})
|
493
|
-
currency = params[:currency] ||
|
493
|
+
currency = params[:currency] || StripeMock.default_currency
|
494
494
|
{
|
495
495
|
id: "2",
|
496
496
|
object: "plan",
|
@@ -591,7 +591,7 @@ module StripeMock
|
|
591
591
|
end
|
592
592
|
|
593
593
|
def self.mock_transfer(params={})
|
594
|
-
currency = params[:currency] ||
|
594
|
+
currency = params[:currency] || StripeMock.default_currency
|
595
595
|
id = params[:id] || 'tr_test_transfer'
|
596
596
|
{
|
597
597
|
:status => 'pending',
|
@@ -623,7 +623,7 @@ module StripeMock
|
|
623
623
|
end
|
624
624
|
|
625
625
|
def self.mock_payout(params={})
|
626
|
-
currency = params[:currency] ||
|
626
|
+
currency = params[:currency] || StripeMock.default_currency
|
627
627
|
id = params[:id] || 'po_test_payout'
|
628
628
|
{
|
629
629
|
:amount => 100,
|
@@ -647,7 +647,7 @@ module StripeMock
|
|
647
647
|
|
648
648
|
def self.mock_dispute(params={})
|
649
649
|
@timestamp ||= Time.now.to_i
|
650
|
-
currency = params[:currency] ||
|
650
|
+
currency = params[:currency] || StripeMock.default_currency
|
651
651
|
id = params[:id] || "dp_test_dispute"
|
652
652
|
{
|
653
653
|
:id => id,
|
@@ -967,7 +967,7 @@ module StripeMock
|
|
967
967
|
end
|
968
968
|
|
969
969
|
def self.mock_balance_transaction(params = {})
|
970
|
-
currency = params[:currency] ||
|
970
|
+
currency = params[:currency] || StripeMock.default_currency
|
971
971
|
bt_id = params[:id] || 'test_txn_default'
|
972
972
|
source = params[:source] || 'ch_test_charge'
|
973
973
|
{
|
@@ -1015,7 +1015,7 @@ module StripeMock
|
|
1015
1015
|
object: 'plan',
|
1016
1016
|
amount: 1337,
|
1017
1017
|
created: 1504716177,
|
1018
|
-
currency:
|
1018
|
+
currency: StripeMock.default_currency,
|
1019
1019
|
interval: 'month',
|
1020
1020
|
interval_count: 1,
|
1021
1021
|
livemode: false,
|
data/lib/stripe_mock/instance.rb
CHANGED
@@ -20,6 +20,7 @@ module StripeMock
|
|
20
20
|
@@handlers.find {|h| method_url =~ h[:route] }
|
21
21
|
end
|
22
22
|
|
23
|
+
include StripeMock::RequestHandlers::ExternalAccounts
|
23
24
|
include StripeMock::RequestHandlers::Accounts
|
24
25
|
include StripeMock::RequestHandlers::Balance
|
25
26
|
include StripeMock::RequestHandlers::BalanceTransactions
|
@@ -41,7 +41,7 @@ module StripeMock
|
|
41
41
|
end
|
42
42
|
|
43
43
|
ensure_required_params(params)
|
44
|
-
bal_trans_params = { amount: params[:amount], source:
|
44
|
+
bal_trans_params = { amount: params[:amount], source: id }
|
45
45
|
|
46
46
|
balance_transaction_id = new_balance_transaction('txn', bal_trans_params)
|
47
47
|
|
@@ -40,7 +40,7 @@ module StripeMock
|
|
40
40
|
end
|
41
41
|
|
42
42
|
subscription = Data.mock_subscription({ id: new_id('su') })
|
43
|
-
subscription
|
43
|
+
subscription = resolve_subscription_changes(subscription, [plan], customers[ params[:id] ], params)
|
44
44
|
add_subscription_to_customer(customers[ params[:id] ], subscription)
|
45
45
|
subscriptions[subscription[:id]] = subscription
|
46
46
|
elsif params[:trial_end]
|
@@ -0,0 +1,55 @@
|
|
1
|
+
module StripeMock
|
2
|
+
module RequestHandlers
|
3
|
+
module ExternalAccounts
|
4
|
+
|
5
|
+
def ExternalAccounts.included(klass)
|
6
|
+
klass.add_handler 'get /v1/accounts/(.*)/external_accounts', :retrieve_external_accounts
|
7
|
+
klass.add_handler 'post /v1/accounts/(.*)/external_accounts', :create_external_account
|
8
|
+
klass.add_handler 'post /v1/accounts/(.*)/external_accounts/(.*)/verify', :verify_external_account
|
9
|
+
klass.add_handler 'get /v1/accounts/(.*)/external_accounts/(.*)', :retrieve_external_account
|
10
|
+
klass.add_handler 'delete /v1/accounts/(.*)/external_accounts/(.*)', :delete_external_account
|
11
|
+
klass.add_handler 'post /v1/accounts/(.*)/external_accounts/(.*)', :update_external_account
|
12
|
+
end
|
13
|
+
|
14
|
+
def create_external_account(route, method_url, params, headers)
|
15
|
+
route =~ method_url
|
16
|
+
add_external_account_to(:account, $1, params, accounts)
|
17
|
+
end
|
18
|
+
|
19
|
+
def retrieve_external_accounts(route, method_url, params, headers)
|
20
|
+
route =~ method_url
|
21
|
+
retrieve_object_cards(:account, $1, accounts)
|
22
|
+
end
|
23
|
+
|
24
|
+
def retrieve_external_account(route, method_url, params, headers)
|
25
|
+
route =~ method_url
|
26
|
+
account = assert_existence :account, $1, accounts[$1]
|
27
|
+
|
28
|
+
assert_existence :card, $2, get_card(account, $2)
|
29
|
+
end
|
30
|
+
|
31
|
+
def delete_external_account(route, method_url, params, headers)
|
32
|
+
route =~ method_url
|
33
|
+
delete_card_from(:account, $1, $2, accounts)
|
34
|
+
end
|
35
|
+
|
36
|
+
def update_external_account(route, method_url, params, headers)
|
37
|
+
route =~ method_url
|
38
|
+
account = assert_existence :account, $1, accounts[$1]
|
39
|
+
|
40
|
+
card = assert_existence :card, $2, get_card(account, $2)
|
41
|
+
card.merge!(params)
|
42
|
+
card
|
43
|
+
end
|
44
|
+
|
45
|
+
def verify_external_account(route, method_url, params, headers)
|
46
|
+
route =~ method_url
|
47
|
+
account = assert_existence :account, $1, accounts[$1]
|
48
|
+
|
49
|
+
external_account = assert_existence :bank_account, $2, verify_bank_account(account, $2)
|
50
|
+
external_account
|
51
|
+
end
|
52
|
+
|
53
|
+
end
|
54
|
+
end
|
55
|
+
end
|
@@ -3,7 +3,7 @@ module StripeMock
|
|
3
3
|
module Helpers
|
4
4
|
|
5
5
|
def verify_bank_account(object, bank_account_id, class_name='Customer')
|
6
|
-
bank_accounts = object[:bank_accounts] || object[:sources]
|
6
|
+
bank_accounts = object[:external_accounts] || object[:bank_accounts] || object[:sources]
|
7
7
|
bank_account = bank_accounts[:data].find{|acc| acc[:id] == bank_account_id }
|
8
8
|
return if bank_account.nil?
|
9
9
|
bank_account['status'] = 'verified'
|
@@ -3,7 +3,7 @@ module StripeMock
|
|
3
3
|
module Helpers
|
4
4
|
|
5
5
|
def get_card(object, card_id, class_name='Customer')
|
6
|
-
cards = object[:cards] || object[:sources]
|
6
|
+
cards = object[:cards] || object[:sources] || object[:external_accounts]
|
7
7
|
card = cards[:data].find{|cc| cc[:id] == card_id }
|
8
8
|
if card.nil?
|
9
9
|
if class_name == 'Recipient'
|
@@ -36,7 +36,7 @@ module StripeMock
|
|
36
36
|
|
37
37
|
def add_card_to_object(type, card, object, replace_current=false)
|
38
38
|
card[type] = object[:id]
|
39
|
-
cards_or_sources = object[:cards] || object[:sources]
|
39
|
+
cards_or_sources = object[:cards] || object[:sources] || object[:external_accounts]
|
40
40
|
|
41
41
|
is_customer = object.has_key?(:sources)
|
42
42
|
|
@@ -58,7 +58,7 @@ module StripeMock
|
|
58
58
|
|
59
59
|
def retrieve_object_cards(type, type_id, objects)
|
60
60
|
resource = assert_existence type, type_id, objects[type_id]
|
61
|
-
cards = resource[:cards] || resource[:sources]
|
61
|
+
cards = resource[:cards] || resource[:sources] || resource[:external_accounts]
|
62
62
|
|
63
63
|
Data.mock_list_object(cards[:data])
|
64
64
|
end
|
@@ -69,7 +69,7 @@ module StripeMock
|
|
69
69
|
assert_existence :card, card_id, get_card(resource, card_id)
|
70
70
|
|
71
71
|
card = { id: card_id, deleted: true }
|
72
|
-
cards_or_sources = resource[:cards] || resource[:sources]
|
72
|
+
cards_or_sources = resource[:cards] || resource[:sources] || resource[:external_accounts]
|
73
73
|
cards_or_sources[:data].reject!{|cc|
|
74
74
|
cc[:id] == card[:id]
|
75
75
|
}
|
@@ -103,7 +103,7 @@ module StripeMock
|
|
103
103
|
def add_card_to(type, type_id, params, objects)
|
104
104
|
resource = assert_existence type, type_id, objects[type_id]
|
105
105
|
|
106
|
-
card = card_from_params(params[:card] || params[:source])
|
106
|
+
card = card_from_params(params[:card] || params[:source] || params[:external_accounts])
|
107
107
|
add_card_to_object(type, card, resource)
|
108
108
|
end
|
109
109
|
|
@@ -0,0 +1,49 @@
|
|
1
|
+
module StripeMock
|
2
|
+
module RequestHandlers
|
3
|
+
module Helpers
|
4
|
+
|
5
|
+
def add_external_account_to(type, type_id, params, objects)
|
6
|
+
resource = assert_existence type, type_id, objects[type_id]
|
7
|
+
|
8
|
+
source =
|
9
|
+
if params[:card]
|
10
|
+
card_from_params(params[:card])
|
11
|
+
elsif params[:bank_account]
|
12
|
+
bank_from_params(params[:bank_account])
|
13
|
+
else
|
14
|
+
begin
|
15
|
+
get_card_by_token(params[:external_account])
|
16
|
+
rescue Stripe::InvalidRequestError
|
17
|
+
bank_from_params(params[:external_account])
|
18
|
+
end
|
19
|
+
end
|
20
|
+
add_external_account_to_object(type, source, resource)
|
21
|
+
end
|
22
|
+
|
23
|
+
def add_external_account_to_object(type, source, object, replace_current=false)
|
24
|
+
source[type] = object[:id]
|
25
|
+
accounts = object[:external_accounts]
|
26
|
+
|
27
|
+
if replace_current && accounts[:data]
|
28
|
+
accounts[:data].delete_if {|source| source[:id] == object[:default_source]}
|
29
|
+
object[:default_source] = source[:id]
|
30
|
+
accounts[:data] = [source]
|
31
|
+
else
|
32
|
+
accounts[:total_count] = (accounts[:total_count] || 0) + 1
|
33
|
+
(accounts[:data] ||= []) << source
|
34
|
+
end
|
35
|
+
object[:default_source] = source[:id] if object[:default_source].nil?
|
36
|
+
|
37
|
+
source
|
38
|
+
end
|
39
|
+
|
40
|
+
def bank_from_params(attrs_or_token)
|
41
|
+
if attrs_or_token.is_a? Hash
|
42
|
+
attrs_or_token = generate_bank_token(attrs_or_token)
|
43
|
+
end
|
44
|
+
get_bank_by_token(attrs_or_token)
|
45
|
+
end
|
46
|
+
|
47
|
+
end
|
48
|
+
end
|
49
|
+
end
|
@@ -6,22 +6,31 @@ module StripeMock
|
|
6
6
|
customer[:subscriptions][:data].find{|sub| sub[:id] == sub_id }
|
7
7
|
end
|
8
8
|
|
9
|
-
def
|
9
|
+
def resolve_subscription_changes(subscription, plans, customer, options = {})
|
10
|
+
subscription.merge!(custom_subscription_params(plans, customer, options))
|
11
|
+
subscription[:items][:data] = plans.map { |plan| Data.mock_subscription_item({ plan: plan }) }
|
12
|
+
subscription
|
13
|
+
end
|
14
|
+
|
15
|
+
def custom_subscription_params(plans, cus, options = {})
|
10
16
|
verify_trial_end(options[:trial_end]) if options[:trial_end]
|
11
17
|
|
18
|
+
plan = plans.first if plans.size == 1
|
19
|
+
|
12
20
|
now = Time.now.utc.to_i
|
13
21
|
created_time = options[:created] || now
|
14
22
|
start_time = options[:current_period_start] || now
|
15
|
-
params = {
|
23
|
+
params = { customer: cus[:id], current_period_start: start_time, created: created_time }
|
24
|
+
params.merge!({ :plan => (plans.size == 1 ? plans.first : nil) })
|
16
25
|
params.merge! options.select {|k,v| k =~ /application_fee_percent|quantity|metadata|tax_percent/}
|
17
26
|
# TODO: Implement coupon logic
|
18
27
|
|
19
28
|
if (((plan && plan[:trial_period_days]) || 0) == 0 && options[:trial_end].nil?) || options[:trial_end] == "now"
|
20
|
-
end_time = get_ending_time(start_time, plan)
|
21
|
-
params.merge!({status: 'active', current_period_end: end_time, trial_start: nil, trial_end: nil})
|
29
|
+
end_time = options[:billing_cycle_anchor] || get_ending_time(start_time, plan)
|
30
|
+
params.merge!({status: 'active', current_period_end: end_time, trial_start: nil, trial_end: nil, billing_cycle_anchor: options[:billing_cycle_anchor]})
|
22
31
|
else
|
23
32
|
end_time = options[:trial_end] || (Time.now.utc.to_i + plan[:trial_period_days]*86400)
|
24
|
-
params.merge!({status: 'trialing', current_period_end: end_time, trial_start: start_time, trial_end: end_time})
|
33
|
+
params.merge!({status: 'trialing', current_period_end: end_time, trial_start: start_time, trial_end: end_time, billing_cycle_anchor: nil})
|
25
34
|
end
|
26
35
|
|
27
36
|
params
|
@@ -87,14 +96,6 @@ module StripeMock
|
|
87
96
|
items.each { |i| total += (i[:quantity] || 1) * i[:plan][:amount] }
|
88
97
|
total
|
89
98
|
end
|
90
|
-
|
91
|
-
def mock_subscription_items(items = [])
|
92
|
-
data = []
|
93
|
-
items.each do |i|
|
94
|
-
data << Data.mock_subscription_item(i.merge(plan: plans[i[:plan].to_s]))
|
95
|
-
end
|
96
|
-
data
|
97
|
-
end
|
98
99
|
end
|
99
100
|
end
|
100
101
|
end
|
@@ -87,7 +87,7 @@ module StripeMock
|
|
87
87
|
invoice_date = Time.now.to_i
|
88
88
|
subscription_plan = assert_existence :plan, subscription_plan_id, plans[subscription_plan_id.to_s]
|
89
89
|
preview_subscription = Data.mock_subscription
|
90
|
-
preview_subscription
|
90
|
+
preview_subscription = resolve_subscription_changes(preview_subscription, [subscription_plan], customer, { trial_end: params[:subscription_trial_end] })
|
91
91
|
preview_subscription[:id] = subscription[:id]
|
92
92
|
preview_subscription[:quantity] = subscription_quantity
|
93
93
|
subscription_proration_date = params[:subscription_proration_date] || Time.now
|
@@ -166,9 +166,9 @@ module StripeMock
|
|
166
166
|
#anonymous charge
|
167
167
|
def invoice_charge(invoice)
|
168
168
|
begin
|
169
|
-
new_charge(nil, nil, {customer: invoice[:customer]["id"], amount: invoice[:amount_due], currency:
|
169
|
+
new_charge(nil, nil, {customer: invoice[:customer]["id"], amount: invoice[:amount_due], currency: StripeMock.default_currency}, nil)
|
170
170
|
rescue Stripe::InvalidRequestError
|
171
|
-
new_charge(nil, nil, {source: generate_card_token, amount: invoice[:amount_due], currency:
|
171
|
+
new_charge(nil, nil, {source: generate_card_token, amount: invoice[:amount_due], currency: StripeMock.default_currency}, nil)
|
172
172
|
end
|
173
173
|
end
|
174
174
|
|
@@ -32,24 +32,10 @@ module StripeMock
|
|
32
32
|
customer[:subscriptions]
|
33
33
|
end
|
34
34
|
|
35
|
-
def plan_id_from_params(params)
|
36
|
-
if params[:plan]
|
37
|
-
params[:plan].to_s
|
38
|
-
elsif params[:items]
|
39
|
-
item = params[:items].values.find { |item| item[:plan] }
|
40
|
-
if item
|
41
|
-
item[:plan].to_s
|
42
|
-
end
|
43
|
-
end
|
44
|
-
end
|
45
|
-
|
46
35
|
def create_customer_subscription(route, method_url, params, headers)
|
47
36
|
route =~ method_url
|
48
37
|
|
49
|
-
|
50
|
-
|
51
|
-
plan = assert_existence :plan, plan_id, plans[plan_id]
|
52
|
-
|
38
|
+
subscription_plans = get_subscription_plans_from_params(params)
|
53
39
|
customer = assert_existence :customer, $1, customers[$1]
|
54
40
|
|
55
41
|
if params[:source]
|
@@ -59,10 +45,11 @@ module StripeMock
|
|
59
45
|
end
|
60
46
|
|
61
47
|
subscription = Data.mock_subscription({ id: (params[:id] || new_id('su')) })
|
62
|
-
subscription
|
48
|
+
subscription = resolve_subscription_changes(subscription, subscription_plans, customer, params)
|
63
49
|
|
64
50
|
# Ensure customer has card to charge if plan has no trial and is not free
|
65
|
-
|
51
|
+
# Note: needs updating for subscriptions with multiple plans
|
52
|
+
verify_card_present(customer, subscription_plans.first, subscription, params)
|
66
53
|
|
67
54
|
if params[:coupon]
|
68
55
|
coupon_id = params[:coupon]
|
@@ -82,25 +69,23 @@ module StripeMock
|
|
82
69
|
subscriptions[subscription[:id]] = subscription
|
83
70
|
add_subscription_to_customer(customer, subscription)
|
84
71
|
|
85
|
-
clear_top_level_plan_if_multiple_items(subscription)
|
86
|
-
|
87
72
|
subscriptions[subscription[:id]]
|
88
73
|
end
|
89
74
|
|
90
75
|
def create_subscription(route, method_url, params, headers)
|
91
76
|
route =~ method_url
|
92
77
|
|
93
|
-
|
94
|
-
|
95
|
-
plan = plan_id ? assert_existence(:plan, plan_id, plans[plan_id]) : nil
|
78
|
+
subscription_plans = get_subscription_plans_from_params(params)
|
96
79
|
|
97
80
|
customer = params[:customer]
|
98
81
|
customer_id = customer.is_a?(Stripe::Customer) ? customer[:id] : customer.to_s
|
99
82
|
customer = assert_existence :customer, customer_id, customers[customer_id]
|
100
83
|
|
101
|
-
if
|
102
|
-
|
103
|
-
|
84
|
+
if subscription_plans && customer
|
85
|
+
subscription_plans.each do |plan|
|
86
|
+
unless customer[:currency].to_s == plan[:currency].to_s
|
87
|
+
raise Stripe::InvalidRequestError.new("Customer's currency of #{customer[:currency]} does not match plan's currency of #{plan[:currency]}", 'currency', http_status: 400)
|
88
|
+
end
|
104
89
|
end
|
105
90
|
end
|
106
91
|
|
@@ -110,18 +95,18 @@ module StripeMock
|
|
110
95
|
customer[:default_source] = new_card[:id]
|
111
96
|
end
|
112
97
|
|
113
|
-
allowed_params = %w(customer application_fee_percent coupon items metadata plan quantity source tax_percent trial_end trial_period_days current_period_start created prorate)
|
98
|
+
allowed_params = %w(customer application_fee_percent coupon items metadata plan quantity source tax_percent trial_end trial_period_days current_period_start created prorate billing_cycle_anchor)
|
114
99
|
unknown_params = params.keys - allowed_params.map(&:to_sym)
|
115
100
|
if unknown_params.length > 0
|
116
101
|
raise Stripe::InvalidRequestError.new("Received unknown parameter: #{unknown_params.join}", unknown_params.first.to_s, http_status: 400)
|
117
102
|
end
|
118
103
|
|
119
104
|
subscription = Data.mock_subscription({ id: (params[:id] || new_id('su')) })
|
120
|
-
subscription
|
121
|
-
subscription[:items][:data] = mock_subscription_items(params[:items].values) if params[:items]
|
105
|
+
subscription = resolve_subscription_changes(subscription, subscription_plans, customer, params)
|
122
106
|
|
123
107
|
# Ensure customer has card to charge if plan has no trial and is not free
|
124
|
-
|
108
|
+
# Note: needs updating for subscriptions with multiple plans
|
109
|
+
verify_card_present(customer, subscription_plans.first, subscription, params)
|
125
110
|
|
126
111
|
if params[:coupon]
|
127
112
|
coupon_id = params[:coupon]
|
@@ -141,8 +126,6 @@ module StripeMock
|
|
141
126
|
subscriptions[subscription[:id]] = subscription
|
142
127
|
add_subscription_to_customer(customer, subscription)
|
143
128
|
|
144
|
-
clear_top_level_plan_if_multiple_items(subscription)
|
145
|
-
|
146
129
|
subscriptions[subscription[:id]]
|
147
130
|
end
|
148
131
|
|
@@ -176,21 +159,12 @@ module StripeMock
|
|
176
159
|
customer[:default_source] = new_card[:id]
|
177
160
|
end
|
178
161
|
|
179
|
-
|
180
|
-
plan_id = plan_id_from_params(params)
|
181
|
-
|
182
|
-
unless plan_id
|
183
|
-
plan_id = if subscription[:plan]
|
184
|
-
subscription[:plan][:id]
|
185
|
-
elsif subscription[:items]
|
186
|
-
row = subscription[:items][:data].find { |item| item[:plan] }
|
187
|
-
if row
|
188
|
-
row[:plan][:id]
|
189
|
-
end
|
190
|
-
end
|
191
|
-
end
|
162
|
+
subscription_plans = get_subscription_plans_from_params(params)
|
192
163
|
|
193
|
-
|
164
|
+
# subscription plans are not being updated but load them for the response
|
165
|
+
if subscription_plans.empty?
|
166
|
+
subscription_plans = subscription[:items][:data].map { |item| item[:plan] }
|
167
|
+
end
|
194
168
|
|
195
169
|
if params[:coupon]
|
196
170
|
coupon_id = params[:coupon]
|
@@ -207,10 +181,7 @@ module StripeMock
|
|
207
181
|
raise Stripe::InvalidRequestError.new("No such coupon: #{coupon_id}", 'coupon', http_status: 400)
|
208
182
|
end
|
209
183
|
end
|
210
|
-
|
211
|
-
assert_existence :plan, plan_id, plan
|
212
|
-
params[:plan] = plan if params[:plan]
|
213
|
-
verify_card_present(customer, plan, subscription)
|
184
|
+
verify_card_present(customer, subscription_plans.first, subscription)
|
214
185
|
|
215
186
|
if subscription[:cancel_at_period_end]
|
216
187
|
subscription[:cancel_at_period_end] = false
|
@@ -218,14 +189,12 @@ module StripeMock
|
|
218
189
|
end
|
219
190
|
|
220
191
|
params[:current_period_start] = subscription[:current_period_start]
|
221
|
-
subscription
|
192
|
+
subscription = resolve_subscription_changes(subscription, subscription_plans, customer, params)
|
222
193
|
|
223
194
|
# delete the old subscription, replace with the new subscription
|
224
195
|
customer[:subscriptions][:data].reject! { |sub| sub[:id] == subscription[:id] }
|
225
196
|
customer[:subscriptions][:data] << subscription
|
226
197
|
|
227
|
-
clear_top_level_plan_if_multiple_items(subscription)
|
228
|
-
|
229
198
|
subscription
|
230
199
|
end
|
231
200
|
|
@@ -259,8 +228,20 @@ module StripeMock
|
|
259
228
|
|
260
229
|
private
|
261
230
|
|
262
|
-
def
|
263
|
-
|
231
|
+
def get_subscription_plans_from_params(params)
|
232
|
+
plan_ids = if params[:plan]
|
233
|
+
[params[:plan].to_s]
|
234
|
+
elsif params[:items]
|
235
|
+
items = params[:items]
|
236
|
+
items = items.values if items.respond_to?(:values)
|
237
|
+
items.map { |item| item[:plan].to_s if item[:plan] }
|
238
|
+
else
|
239
|
+
[]
|
240
|
+
end
|
241
|
+
plan_ids.each do |plan_id|
|
242
|
+
assert_existence :plan, plan_id, plans[plan_id]
|
243
|
+
end
|
244
|
+
plan_ids.map { |plan_id| plans[plan_id] }
|
264
245
|
end
|
265
246
|
|
266
247
|
def verify_card_present(customer, plan, subscription, params={})
|
@@ -3,7 +3,7 @@ module StripeMock
|
|
3
3
|
class Base
|
4
4
|
|
5
5
|
def create_plan_params(params={})
|
6
|
-
currency = params[:currency] ||
|
6
|
+
currency = params[:currency] || StripeMock.default_currency
|
7
7
|
{
|
8
8
|
:id => 'stripe_mock_default_plan_id',
|
9
9
|
:name => 'StripeMock Default Plan ID',
|
@@ -23,7 +23,7 @@ module StripeMock
|
|
23
23
|
end
|
24
24
|
|
25
25
|
def generate_bank_token(bank_account_params={})
|
26
|
-
currency = bank_account_params[:currency] ||
|
26
|
+
currency = bank_account_params[:currency] || StripeMock.default_currency
|
27
27
|
bank_account = {
|
28
28
|
:country => "US",
|
29
29
|
:currency => currency,
|
@@ -39,7 +39,7 @@ module StripeMock
|
|
39
39
|
end
|
40
40
|
|
41
41
|
def create_coupon_params(params = {})
|
42
|
-
currency = params[:currency] ||
|
42
|
+
currency = params[:currency] || StripeMock.default_currency
|
43
43
|
{
|
44
44
|
id: '10BUCKS',
|
45
45
|
amount_off: 1000,
|
data/lib/stripe_mock/version.rb
CHANGED
data/spec/instance_spec.rb
CHANGED
@@ -52,4 +52,18 @@ describe StripeMock::Instance do
|
|
52
52
|
StripeMock.set_conversion_rate(1.25)
|
53
53
|
expect(StripeMock.instance.conversion_rate).to eq(1.25)
|
54
54
|
end
|
55
|
+
|
56
|
+
it "allows non-usd default currency" do
|
57
|
+
old_default_currency = StripeMock.default_currency
|
58
|
+
customer = begin
|
59
|
+
StripeMock.default_currency = "jpy"
|
60
|
+
Stripe::Customer.create({
|
61
|
+
email: 'johnny@appleseed.com',
|
62
|
+
source: stripe_helper.generate_card_token
|
63
|
+
})
|
64
|
+
ensure
|
65
|
+
StripeMock.default_currency = old_default_currency
|
66
|
+
end
|
67
|
+
expect(customer.currency).to eq("jpy")
|
68
|
+
end
|
55
69
|
end
|
@@ -40,7 +40,7 @@ shared_examples 'Bank API' do
|
|
40
40
|
expect(bank.last4).to eq("6789")
|
41
41
|
end
|
42
42
|
|
43
|
-
it "creates a single bank with a generated bank token"
|
43
|
+
it "creates a single bank with a generated bank token" do
|
44
44
|
customer = Stripe::Customer.create
|
45
45
|
expect(customer.sources.count).to eq 0
|
46
46
|
|
@@ -171,7 +171,7 @@ shared_examples 'Charge API' do
|
|
171
171
|
bal_trans = Stripe::BalanceTransaction.retrieve(charge.balance_transaction)
|
172
172
|
expect(bal_trans.amount).to eq(charge.amount)
|
173
173
|
expect(bal_trans.fee).to eq(39)
|
174
|
-
expect(bal_trans.source).to eq(charge.
|
174
|
+
expect(bal_trans.source).to eq(charge.id)
|
175
175
|
end
|
176
176
|
|
177
177
|
context 'when conversion rate is set' do
|
@@ -220,8 +220,8 @@ shared_examples 'Customer API' do
|
|
220
220
|
end
|
221
221
|
|
222
222
|
describe 'repeating coupon with duration limit', live: true do
|
223
|
-
let!(:coupon) {
|
224
|
-
let!(:customer) { Stripe::Customer.create(coupon:
|
223
|
+
let!(:coupon) { stripe_helper.create_coupon(id: '10OFF', amount_off: 1000, currency: 'usd', duration: 'repeating', duration_in_months: 12) }
|
224
|
+
let!(:customer) { Stripe::Customer.create(coupon: coupon.id) }
|
225
225
|
it 'creates the discount with the end date', live: true do
|
226
226
|
discount = Stripe::Customer.retrieve(customer.id).discount
|
227
227
|
expect(discount).to_not be_nil
|
@@ -0,0 +1,170 @@
|
|
1
|
+
require 'spec_helper'
|
2
|
+
|
3
|
+
shared_examples 'External Account API' do
|
4
|
+
|
5
|
+
it 'creates/returns a bank when using account.external_accounts.create given a bank token' do
|
6
|
+
account = Stripe::Account.create(id: 'test_account', type: 'custom', country: "US")
|
7
|
+
bank_token = stripe_helper.generate_bank_token(last4: "1123", exp_month: 11, exp_year: 2099)
|
8
|
+
bank = account.external_accounts.create(external_account: bank_token)
|
9
|
+
|
10
|
+
expect(bank.account).to eq('test_account')
|
11
|
+
expect(bank.last4).to eq("1123")
|
12
|
+
expect(bank.exp_month).to eq(11)
|
13
|
+
expect(bank.exp_year).to eq(2099)
|
14
|
+
|
15
|
+
account = Stripe::Account.retrieve('test_account')
|
16
|
+
expect(account.external_accounts.count).to eq(1)
|
17
|
+
bank = account.external_accounts.first
|
18
|
+
expect(bank.account).to eq('test_account')
|
19
|
+
expect(bank.last4).to eq("1123")
|
20
|
+
expect(bank.exp_month).to eq(11)
|
21
|
+
expect(bank.exp_year).to eq(2099)
|
22
|
+
end
|
23
|
+
|
24
|
+
it 'creates/returns a bank when using account.external_accounts.create given bank params' do
|
25
|
+
account = Stripe::Account.create(id: 'test_account', type: 'custom', country: "US")
|
26
|
+
bank = account.external_accounts.create(external_account: {
|
27
|
+
object: 'bank_account',
|
28
|
+
account_number: '000123456789',
|
29
|
+
routing_number: '110000000',
|
30
|
+
country: 'US',
|
31
|
+
currency: 'usd'
|
32
|
+
})
|
33
|
+
|
34
|
+
expect(bank.account).to eq('test_account')
|
35
|
+
expect(bank.routing_number).to eq('110000000')
|
36
|
+
expect(bank.country).to eq('US')
|
37
|
+
expect(bank.currency).to eq('usd')
|
38
|
+
|
39
|
+
account = Stripe::Account.retrieve('test_account')
|
40
|
+
expect(account.external_accounts.count).to eq(1)
|
41
|
+
bank = account.external_accounts.first
|
42
|
+
expect(bank.account).to eq('test_account')
|
43
|
+
expect(bank.routing_number).to eq('110000000')
|
44
|
+
expect(bank.country).to eq('US')
|
45
|
+
expect(bank.currency).to eq('usd')
|
46
|
+
end
|
47
|
+
|
48
|
+
it "creates a single bank with a generated bank token" do
|
49
|
+
account = Stripe::Account.create(type: 'custom', country: "US")
|
50
|
+
expect(account.external_accounts.count).to eq 0
|
51
|
+
|
52
|
+
account.external_accounts.create external_account: stripe_helper.generate_bank_token
|
53
|
+
# Yes, stripe-ruby does not actually add the new bank to the account instance
|
54
|
+
expect(account.external_accounts.count).to eq 0
|
55
|
+
|
56
|
+
account2 = Stripe::Account.retrieve(account.id)
|
57
|
+
expect(account2.external_accounts.count).to eq 1
|
58
|
+
end
|
59
|
+
|
60
|
+
describe "retrieval and deletion with accounts" do
|
61
|
+
let!(:account) { Stripe::Account.create(id: 'test_account', type: 'custom', country: "US") }
|
62
|
+
let!(:bank_token) { stripe_helper.generate_bank_token(last4: "1123", exp_month: 11, exp_year: 2099) }
|
63
|
+
let!(:bank) { account.external_accounts.create(external_account: bank_token) }
|
64
|
+
|
65
|
+
it "can retrieve all account's banks" do
|
66
|
+
retrieved = account.external_accounts.all
|
67
|
+
expect(retrieved.count).to eq(1)
|
68
|
+
end
|
69
|
+
|
70
|
+
it "retrieves an account bank" do
|
71
|
+
retrieved = account.external_accounts.retrieve(bank.id)
|
72
|
+
expect(retrieved.to_s).to eq(bank.to_s)
|
73
|
+
end
|
74
|
+
|
75
|
+
it "retrieves an account's bank after re-fetching the account" do
|
76
|
+
retrieved = Stripe::Account.retrieve(account.id).external_accounts.retrieve(bank.id)
|
77
|
+
expect(retrieved.id).to eq bank.id
|
78
|
+
end
|
79
|
+
|
80
|
+
it "deletes an accounts bank" do
|
81
|
+
bank.delete
|
82
|
+
retrieved_acct = Stripe::Account.retrieve(account.id)
|
83
|
+
expect(retrieved_acct.external_accounts.data).to be_empty
|
84
|
+
end
|
85
|
+
|
86
|
+
context "deletion when the user has two external accounts" do
|
87
|
+
let!(:bank_token_2) { stripe_helper.generate_bank_token(last4: "1123", exp_month: 11, exp_year: 2099) }
|
88
|
+
let!(:bank_2) { account.external_accounts.create(external_account: bank_token_2) }
|
89
|
+
|
90
|
+
it "has just one bank anymore" do
|
91
|
+
bank.delete
|
92
|
+
retrieved_acct = Stripe::Account.retrieve(account.id)
|
93
|
+
expect(retrieved_acct.external_accounts.data.count).to eq 1
|
94
|
+
expect(retrieved_acct.external_accounts.data.first.id).to eq bank_2.id
|
95
|
+
end
|
96
|
+
end
|
97
|
+
end
|
98
|
+
|
99
|
+
describe "Errors" do
|
100
|
+
it "throws an error when the account does not have the retrieving bank id" do
|
101
|
+
account = Stripe::Account.create(type: 'custom', country: "US")
|
102
|
+
bank_id = "bank_123"
|
103
|
+
expect { account.external_accounts.retrieve(bank_id) }.to raise_error {|e|
|
104
|
+
expect(e).to be_a Stripe::InvalidRequestError
|
105
|
+
expect(e.message).to match /no.*source/i
|
106
|
+
expect(e.message).to include bank_id
|
107
|
+
expect(e.param).to eq 'id'
|
108
|
+
expect(e.http_status).to eq 404
|
109
|
+
}
|
110
|
+
end
|
111
|
+
end
|
112
|
+
|
113
|
+
context "update bank" do
|
114
|
+
let!(:account) { Stripe::Account.create(id: 'test_account', type: 'custom', country: "US") }
|
115
|
+
let!(:bank_token) { stripe_helper.generate_bank_token(last4: "1123", exp_month: 11, exp_year: 2099) }
|
116
|
+
let!(:bank) { account.external_accounts.create(external_account: bank_token) }
|
117
|
+
|
118
|
+
it "updates the bank" do
|
119
|
+
exp_month = 10
|
120
|
+
exp_year = 2098
|
121
|
+
|
122
|
+
bank.exp_month = exp_month
|
123
|
+
bank.exp_year = exp_year
|
124
|
+
bank.save
|
125
|
+
|
126
|
+
retrieved = account.external_accounts.retrieve(bank.id)
|
127
|
+
|
128
|
+
expect(retrieved.exp_month).to eq(exp_month)
|
129
|
+
expect(retrieved.exp_year).to eq(exp_year)
|
130
|
+
end
|
131
|
+
end
|
132
|
+
|
133
|
+
context "retrieve multiple banks" do
|
134
|
+
|
135
|
+
it "retrieves a list of multiple banks" do
|
136
|
+
account = Stripe::Account.create(id: 'test_account', type: 'custom', country: "US")
|
137
|
+
|
138
|
+
bank_token = stripe_helper.generate_bank_token(last4: "1123", exp_month: 11, exp_year: 2099)
|
139
|
+
bank1 = account.external_accounts.create(external_accout: bank_token)
|
140
|
+
bank_token = stripe_helper.generate_bank_token(last4: "1124", exp_month: 12, exp_year: 2098)
|
141
|
+
bank2 = account.external_accounts.create(external_account: bank_token)
|
142
|
+
|
143
|
+
account = Stripe::Account.retrieve('test_account')
|
144
|
+
|
145
|
+
list = account.external_accounts.all
|
146
|
+
|
147
|
+
expect(list.object).to eq("list")
|
148
|
+
expect(list.count).to eq(2)
|
149
|
+
expect(list.data.length).to eq(2)
|
150
|
+
|
151
|
+
expect(list.data.first.object).to eq("bank_account")
|
152
|
+
expect(list.data.first.to_hash).to eq(bank1.to_hash)
|
153
|
+
|
154
|
+
expect(list.data.last.object).to eq("bank_account")
|
155
|
+
expect(list.data.last.to_hash).to eq(bank2.to_hash)
|
156
|
+
end
|
157
|
+
|
158
|
+
it "retrieves an empty list if there's no subscriptions" do
|
159
|
+
Stripe::Account.create(id: 'no_banks', type: 'custom', country: "US")
|
160
|
+
account = Stripe::Account.retrieve('no_banks')
|
161
|
+
|
162
|
+
list = account.external_accounts.all
|
163
|
+
|
164
|
+
expect(list.object).to eq("list")
|
165
|
+
expect(list.count).to eq(0)
|
166
|
+
expect(list.data.length).to eq(0)
|
167
|
+
end
|
168
|
+
end
|
169
|
+
|
170
|
+
end
|
@@ -107,12 +107,12 @@ shared_examples 'Invoice API' do
|
|
107
107
|
end
|
108
108
|
|
109
109
|
context "retrieving upcoming invoice" do
|
110
|
-
let(:customer) {
|
111
|
-
let(:coupon_amtoff) {
|
112
|
-
let(:coupon_pctoff) {
|
113
|
-
let(:plan) {
|
110
|
+
let(:customer) { Stripe::Customer.create(source: stripe_helper.generate_card_token) }
|
111
|
+
let(:coupon_amtoff) { stripe_helper.create_coupon(id: '100OFF', currency: 'usd', amount_off: 100_00, duration: 'repeating', duration_in_months: 6) }
|
112
|
+
let(:coupon_pctoff) { stripe_helper.create_coupon(id: '50%OFF', currency: 'usd', percent_off: 50, amount_off: nil, duration: 'repeating', duration_in_months: 6) }
|
113
|
+
let(:plan) { stripe_helper.create_plan(id: '50m', amount: 50_00, interval: 'month', name: '50m', currency: 'usd') }
|
114
114
|
let(:quantity) { 3 }
|
115
|
-
let(:subscription) {
|
115
|
+
let(:subscription) { Stripe::Subscription.create(plan: plan.id, customer: customer.id, quantity: quantity) }
|
116
116
|
|
117
117
|
before(with_customer: true) { customer }
|
118
118
|
before(with_coupon_amtoff: true) { coupon_amtoff }
|
@@ -122,11 +122,11 @@ shared_examples 'Invoice API' do
|
|
122
122
|
before(with_plan: true) { plan }
|
123
123
|
before(with_subscription: true) { subscription }
|
124
124
|
|
125
|
-
after { subscription.delete rescue nil if @teardown_subscription }
|
126
|
-
after { plan.delete rescue nil if @teardown_plan }
|
127
|
-
after { coupon_pctoff.delete rescue nil if @teardown_coupon_pctoff }
|
128
|
-
after { coupon_amtoff.delete rescue nil if @teardown_coupon_amtoff }
|
129
|
-
after { customer.delete rescue nil if @teardown_customer }
|
125
|
+
# after { subscription.delete rescue nil if @teardown_subscription }
|
126
|
+
# after { plan.delete rescue nil if @teardown_plan }
|
127
|
+
# after { coupon_pctoff.delete rescue nil if @teardown_coupon_pctoff }
|
128
|
+
# after { coupon_amtoff.delete rescue nil if @teardown_coupon_amtoff }
|
129
|
+
# after { customer.delete rescue nil if @teardown_customer }
|
130
130
|
|
131
131
|
describe 'parameter validation' do
|
132
132
|
it 'fails without parameters' do
|
@@ -248,8 +248,9 @@ shared_examples 'Invoice API' do
|
|
248
248
|
|
249
249
|
[false, true].each do |with_trial|
|
250
250
|
describe "prorating a subscription with a new plan, with_trial: #{with_trial}" do
|
251
|
-
let(:new_monthly_plan) {
|
252
|
-
let(:new_yearly_plan) {
|
251
|
+
let(:new_monthly_plan) { stripe_helper.create_plan(id: '100m', amount: 100_00, interval: 'month', name: '100m', currency: 'usd') }
|
252
|
+
let(:new_yearly_plan) { stripe_helper.create_plan(id: '100y', amount: 100_00, interval: 'year', name: '100y', currency: 'usd') }
|
253
|
+
let(:plan) { stripe_helper.create_plan(id: '50m', amount: 50_00, interval: 'month', name: '50m', currency: 'usd') }
|
253
254
|
|
254
255
|
it 'prorates while maintaining billing interval', live: true do
|
255
256
|
# Given
|
@@ -341,8 +342,8 @@ shared_examples 'Invoice API' do
|
|
341
342
|
expect(upcoming.lines.data[1].quantity).to eq new_quantity
|
342
343
|
end
|
343
344
|
|
344
|
-
after { new_monthly_plan.delete rescue nil if @teardown_monthly_plan }
|
345
|
-
after { new_yearly_plan.delete rescue nil if @teardown_yearly_plan }
|
345
|
+
# after { new_monthly_plan.delete rescue nil if @teardown_monthly_plan }
|
346
|
+
# after { new_yearly_plan.delete rescue nil if @teardown_yearly_plan }
|
346
347
|
end
|
347
348
|
end
|
348
349
|
|
@@ -30,6 +30,17 @@ shared_examples 'Plan API' do
|
|
30
30
|
end
|
31
31
|
|
32
32
|
|
33
|
+
it "creates a stripe plan without specifying ID" do
|
34
|
+
plan = Stripe::Plan.create(
|
35
|
+
:name => 'The Mock Plan',
|
36
|
+
:amount => 9900,
|
37
|
+
:currency => 'USD',
|
38
|
+
:interval => 1,
|
39
|
+
)
|
40
|
+
|
41
|
+
expect(plan.id).to match(/^test_plan/)
|
42
|
+
end
|
43
|
+
|
33
44
|
it "stores a created stripe plan in memory" do
|
34
45
|
plan = Stripe::Plan.create(
|
35
46
|
:id => 'pid_2',
|
@@ -283,6 +283,7 @@ shared_examples 'Customer Subscriptions' do
|
|
283
283
|
expect(sub.object).to eq('subscription')
|
284
284
|
expect(sub.plan.to_hash).to eq(plan.to_hash)
|
285
285
|
expect(sub.trial_end - sub.trial_start).to eq(14 * 86400)
|
286
|
+
expect(sub.billing_cycle_anchor).to be_nil
|
286
287
|
|
287
288
|
customer = Stripe::Customer.retrieve('cardless')
|
288
289
|
expect(customer.subscriptions.data).to_not be_empty
|
@@ -398,6 +399,18 @@ shared_examples 'Customer Subscriptions' do
|
|
398
399
|
}
|
399
400
|
end
|
400
401
|
|
402
|
+
it 'overrides current period end when billing cycle anchor is set' do
|
403
|
+
plan = stripe_helper.create_plan(id: 'plan', amount: 999)
|
404
|
+
customer = Stripe::Customer.create(source: gen_card_tk)
|
405
|
+
billing_cycle_anchor = Time.now.utc.to_i + 3600
|
406
|
+
|
407
|
+
sub = Stripe::Subscription.create({ plan: 'plan', customer: customer.id, billing_cycle_anchor: billing_cycle_anchor })
|
408
|
+
|
409
|
+
expect(sub.status).to eq('active')
|
410
|
+
expect(sub.current_period_end).to eq(billing_cycle_anchor)
|
411
|
+
expect(sub.billing_cycle_anchor).to eq(billing_cycle_anchor)
|
412
|
+
end
|
413
|
+
|
401
414
|
it 'when plan defined inside items', live: true do
|
402
415
|
plan = stripe_helper.create_plan(id: 'BASE_PRICE_PLAN1')
|
403
416
|
|
@@ -504,6 +517,57 @@ shared_examples 'Customer Subscriptions' do
|
|
504
517
|
expect(customer.subscriptions.data.first.customer).to eq(customer.id)
|
505
518
|
end
|
506
519
|
|
520
|
+
it "updates a stripe customer's existing subscription with single plan when multiple plans inside of items" do
|
521
|
+
silver_plan = stripe_helper.create_plan(id: 'silver')
|
522
|
+
gold_plan = stripe_helper.create_plan(id: 'gold')
|
523
|
+
addon_plan = stripe_helper.create_plan(id: 'addon_plan')
|
524
|
+
customer = Stripe::Customer.create(id: 'test_customer_sub', source: gen_card_tk, plan: silver_plan.id)
|
525
|
+
|
526
|
+
sub = Stripe::Subscription.retrieve(customer.subscriptions.data.first.id)
|
527
|
+
sub.items = [{ plan: gold_plan.id, quantity: 2 }, { plan: addon_plan.id, quantity: 2 }]
|
528
|
+
expect(sub.save).to be_truthy
|
529
|
+
|
530
|
+
expect(sub.object).to eq('subscription')
|
531
|
+
expect(sub.plan).to be_nil
|
532
|
+
|
533
|
+
customer = Stripe::Customer.retrieve('test_customer_sub')
|
534
|
+
expect(customer.subscriptions.data).to_not be_empty
|
535
|
+
expect(customer.subscriptions.count).to eq(1)
|
536
|
+
expect(customer.subscriptions.data.length).to eq(1)
|
537
|
+
|
538
|
+
expect(customer.subscriptions.data.first.id).to eq(sub.id)
|
539
|
+
expect(customer.subscriptions.data.first.plan).to be_nil
|
540
|
+
expect(customer.subscriptions.data.first.customer).to eq(customer.id)
|
541
|
+
expect(customer.subscriptions.data.first.items.data[0].plan.to_hash).to eq(gold_plan.to_hash)
|
542
|
+
expect(customer.subscriptions.data.first.items.data[1].plan.to_hash).to eq(addon_plan.to_hash)
|
543
|
+
end
|
544
|
+
|
545
|
+
it "updates a stripe customer's existing subscription with multple plans when multiple plans inside of items" do
|
546
|
+
silver_plan = stripe_helper.create_plan(id: 'silver')
|
547
|
+
gold_plan = stripe_helper.create_plan(id: 'gold')
|
548
|
+
addon1_plan = stripe_helper.create_plan(id: 'addon1')
|
549
|
+
addon2_plan = stripe_helper.create_plan(id: 'addon2')
|
550
|
+
customer = Stripe::Customer.create(id: 'test_customer_sub', source: gen_card_tk)
|
551
|
+
sub = Stripe::Subscription.create(customer: customer.id, items: [{ plan: silver_plan.id }, { plan: addon1_plan.id }])
|
552
|
+
|
553
|
+
sub.items = [{ plan: gold_plan.id, quantity: 2 }, { plan: addon2_plan.id, quantity: 2 }]
|
554
|
+
expect(sub.save).to be_truthy
|
555
|
+
|
556
|
+
expect(sub.object).to eq('subscription')
|
557
|
+
expect(sub.plan).to be_nil
|
558
|
+
|
559
|
+
customer = Stripe::Customer.retrieve('test_customer_sub')
|
560
|
+
expect(customer.subscriptions.data).to_not be_empty
|
561
|
+
expect(customer.subscriptions.count).to eq(1)
|
562
|
+
expect(customer.subscriptions.data.length).to eq(1)
|
563
|
+
|
564
|
+
expect(customer.subscriptions.data.first.id).to eq(sub.id)
|
565
|
+
expect(customer.subscriptions.data.first.plan).to be_nil
|
566
|
+
expect(customer.subscriptions.data.first.customer).to eq(customer.id)
|
567
|
+
expect(customer.subscriptions.data.first.items.data[0].plan.to_hash).to eq(gold_plan.to_hash)
|
568
|
+
expect(customer.subscriptions.data.first.items.data[1].plan.to_hash).to eq(addon2_plan.to_hash)
|
569
|
+
end
|
570
|
+
|
507
571
|
it 'when adds coupon', live: true do
|
508
572
|
plan = stripe_helper.create_plan(id: 'plan_with_coupon2', name: 'One More Test Plan', amount: 777)
|
509
573
|
coupon = stripe_helper.create_coupon
|
@@ -857,13 +921,13 @@ shared_examples 'Customer Subscriptions' do
|
|
857
921
|
expect(subscription.items.object).to eq('list')
|
858
922
|
expect(subscription.items.data.class).to eq(Array)
|
859
923
|
expect(subscription.items.data.count).to eq(1)
|
860
|
-
expect(subscription.items.data.first.id).to eq('
|
861
|
-
expect(subscription.items.data.first.created).to eq(
|
924
|
+
expect(subscription.items.data.first.id).to eq('test_txn_default')
|
925
|
+
expect(subscription.items.data.first.created).to eq(1504716183)
|
862
926
|
expect(subscription.items.data.first.object).to eq('subscription_item')
|
863
|
-
expect(subscription.items.data.first.plan.amount).to eq(
|
864
|
-
expect(subscription.items.data.first.plan.created).to eq(
|
927
|
+
expect(subscription.items.data.first.plan.amount).to eq(0)
|
928
|
+
expect(subscription.items.data.first.plan.created).to eq(1466698898)
|
865
929
|
expect(subscription.items.data.first.plan.currency).to eq('usd')
|
866
|
-
expect(subscription.items.data.first.quantity).to eq(
|
930
|
+
expect(subscription.items.data.first.quantity).to eq(2)
|
867
931
|
end
|
868
932
|
end
|
869
933
|
|
@@ -13,6 +13,7 @@ def it_behaves_like_stripe(&block)
|
|
13
13
|
it_behaves_like 'Card API', &block
|
14
14
|
it_behaves_like 'Charge API', &block
|
15
15
|
it_behaves_like 'Bank API', &block
|
16
|
+
it_behaves_like 'External Account API', &block
|
16
17
|
it_behaves_like 'Coupon API', &block
|
17
18
|
it_behaves_like 'Customer API', &block
|
18
19
|
it_behaves_like 'Dispute API', &block
|
metadata
CHANGED
@@ -1,14 +1,14 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: stripe-ruby-mock
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 2.5.
|
4
|
+
version: 2.5.4
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Gilbert
|
8
8
|
autorequire:
|
9
9
|
bindir: bin
|
10
10
|
cert_chain: []
|
11
|
-
date: 2018-
|
11
|
+
date: 2018-05-04 00:00:00.000000000 Z
|
12
12
|
dependencies:
|
13
13
|
- !ruby/object:Gem::Dependency
|
14
14
|
name: stripe
|
@@ -105,7 +105,6 @@ files:
|
|
105
105
|
- .gitignore
|
106
106
|
- .rspec
|
107
107
|
- .travis.yml
|
108
|
-
- ChangeLog.rdoc
|
109
108
|
- Gemfile
|
110
109
|
- LICENSE.txt
|
111
110
|
- README.md
|
@@ -146,10 +145,12 @@ files:
|
|
146
145
|
- lib/stripe_mock/request_handlers/customers.rb
|
147
146
|
- lib/stripe_mock/request_handlers/disputes.rb
|
148
147
|
- lib/stripe_mock/request_handlers/events.rb
|
148
|
+
- lib/stripe_mock/request_handlers/external_accounts.rb
|
149
149
|
- lib/stripe_mock/request_handlers/helpers/bank_account_helpers.rb
|
150
150
|
- lib/stripe_mock/request_handlers/helpers/card_helpers.rb
|
151
151
|
- lib/stripe_mock/request_handlers/helpers/charge_helpers.rb
|
152
152
|
- lib/stripe_mock/request_handlers/helpers/coupon_helpers.rb
|
153
|
+
- lib/stripe_mock/request_handlers/helpers/external_account_helpers.rb
|
153
154
|
- lib/stripe_mock/request_handlers/helpers/subscription_helpers.rb
|
154
155
|
- lib/stripe_mock/request_handlers/helpers/token_helpers.rb
|
155
156
|
- lib/stripe_mock/request_handlers/invoice_items.rb
|
@@ -238,6 +239,7 @@ files:
|
|
238
239
|
- spec/shared_stripe_examples/customer_examples.rb
|
239
240
|
- spec/shared_stripe_examples/dispute_examples.rb
|
240
241
|
- spec/shared_stripe_examples/error_mock_examples.rb
|
242
|
+
- spec/shared_stripe_examples/external_account_examples.rb
|
241
243
|
- spec/shared_stripe_examples/extra_features_examples.rb
|
242
244
|
- spec/shared_stripe_examples/invoice_examples.rb
|
243
245
|
- spec/shared_stripe_examples/invoice_item_examples.rb
|
@@ -304,6 +306,7 @@ test_files:
|
|
304
306
|
- spec/shared_stripe_examples/customer_examples.rb
|
305
307
|
- spec/shared_stripe_examples/dispute_examples.rb
|
306
308
|
- spec/shared_stripe_examples/error_mock_examples.rb
|
309
|
+
- spec/shared_stripe_examples/external_account_examples.rb
|
307
310
|
- spec/shared_stripe_examples/extra_features_examples.rb
|
308
311
|
- spec/shared_stripe_examples/invoice_examples.rb
|
309
312
|
- spec/shared_stripe_examples/invoice_item_examples.rb
|
data/ChangeLog.rdoc
DELETED