chargebee 1.7.4

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 (39) hide show
  1. checksums.yaml +7 -0
  2. data/CHANGELOG.md +528 -0
  3. data/LICENSE +24 -0
  4. data/README.rdoc +34 -0
  5. data/Rakefile +150 -0
  6. data/chargebee.gemspec +72 -0
  7. data/lib/chargebee.rb +59 -0
  8. data/lib/chargebee/environment.rb +23 -0
  9. data/lib/chargebee/errors.rb +43 -0
  10. data/lib/chargebee/list_result.rb +28 -0
  11. data/lib/chargebee/models/addon.rb +31 -0
  12. data/lib/chargebee/models/address.rb +19 -0
  13. data/lib/chargebee/models/card.rb +32 -0
  14. data/lib/chargebee/models/comment.rb +26 -0
  15. data/lib/chargebee/models/coupon.rb +25 -0
  16. data/lib/chargebee/models/coupon_code.rb +18 -0
  17. data/lib/chargebee/models/customer.rb +77 -0
  18. data/lib/chargebee/models/download.rb +10 -0
  19. data/lib/chargebee/models/estimate.rb +36 -0
  20. data/lib/chargebee/models/event.rb +46 -0
  21. data/lib/chargebee/models/hosted_page.rb +50 -0
  22. data/lib/chargebee/models/invoice.rb +114 -0
  23. data/lib/chargebee/models/model.rb +70 -0
  24. data/lib/chargebee/models/order.rb +31 -0
  25. data/lib/chargebee/models/payment_intent.rb +27 -0
  26. data/lib/chargebee/models/plan.rb +33 -0
  27. data/lib/chargebee/models/portal_session.rb +31 -0
  28. data/lib/chargebee/models/subscription.rb +86 -0
  29. data/lib/chargebee/models/transaction.rb +45 -0
  30. data/lib/chargebee/request.rb +16 -0
  31. data/lib/chargebee/rest.rb +90 -0
  32. data/lib/chargebee/result.rb +100 -0
  33. data/lib/chargebee/util.rb +56 -0
  34. data/lib/ssl/ca-certs.crt +3385 -0
  35. data/spec/chargebee/list_result_spec.rb +53 -0
  36. data/spec/chargebee_spec.rb +99 -0
  37. data/spec/sample_response.rb +73 -0
  38. data/spec/spec_helper.rb +24 -0
  39. metadata +145 -0
@@ -0,0 +1,70 @@
1
+ require 'uri'
2
+
3
+ module ChargeBee
4
+ class Model
5
+
6
+ def initialize(values, sub_types={})
7
+ @values = values
8
+ @sub_types = sub_types
9
+ end
10
+
11
+ def to_s(*args)
12
+ JSON.pretty_generate(@values)
13
+ end
14
+
15
+ def inspect()
16
+ "#<#{self.class}:0x#{self.object_id.to_s(16)} > JSON: " + JSON.pretty_generate(@values)
17
+ end
18
+
19
+ def load(values)
20
+ instance_eval do
21
+ values.each do |k, v|
22
+ set_val = nil
23
+ case v
24
+ when Hash
25
+ set_val = (@sub_types[k] != nil) ? @sub_types[k].construct(v) : v
26
+ when Array
27
+ if(@sub_types[k] != nil)
28
+ set_val = v.map { |item| @sub_types[k].construct(item)}
29
+ else
30
+ set_val = v
31
+ end
32
+ else
33
+ set_val = v
34
+ end
35
+ instance_variable_set("@#{k}", set_val)
36
+ end
37
+ end
38
+ end
39
+
40
+ def method_missing(m, *args, &block)
41
+ if(@values.has_key?(m))
42
+ return @values[m]
43
+ elsif(m[0,3] == "cf_") # All the custom fields start with prefix cf_.
44
+ return nil
45
+ end
46
+ puts "There's no method called #{m} #{args} here -- please try again."
47
+ puts @values
48
+ end
49
+
50
+ def self.uri_path(*paths)
51
+ url = ""
52
+ for path in paths
53
+ if(path.nil? || path.strip.length < 1)
54
+ raise "Id is empty or nil"
55
+ end
56
+ url = "#{url}/#{URI.encode(path.strip)}"
57
+ end
58
+ return url
59
+ end
60
+
61
+ def self.construct(values, sub_types = {})
62
+ if(values != nil)
63
+ obj = self.new(values, sub_types)
64
+ obj.load(values)
65
+ obj
66
+ end
67
+ end
68
+
69
+ end
70
+ end
@@ -0,0 +1,31 @@
1
+ module ChargeBee
2
+ class Order < Model
3
+
4
+ attr_accessor :id, :invoice_id, :status, :reference_id, :fulfillment_status, :note, :tracking_id,
5
+ :batch_id, :created_by, :created_at, :status_update_at
6
+
7
+ # OPERATIONS
8
+ #-----------
9
+
10
+ def self.create(params, env=nil, headers={})
11
+ Request.send('post', uri_path("orders"), params, env, headers)
12
+ end
13
+
14
+ def self.update(id, params={}, env=nil, headers={})
15
+ Request.send('post', uri_path("orders",id.to_s), params, env, headers)
16
+ end
17
+
18
+ def self.retrieve(id, env=nil, headers={})
19
+ Request.send('get', uri_path("orders",id.to_s), {}, env, headers)
20
+ end
21
+
22
+ def self.list(params={}, env=nil, headers={})
23
+ Request.send('get', uri_path("orders"), params, env, headers)
24
+ end
25
+
26
+ def self.orders_for_invoice(id, params={}, env=nil, headers={})
27
+ Request.send('get', uri_path("invoices",id.to_s,"orders"), params, env, headers)
28
+ end
29
+
30
+ end # ~Order
31
+ end # ~ChargeBee
@@ -0,0 +1,27 @@
1
+ module ChargeBee
2
+ class PaymentIntent < Model
3
+
4
+ class PaymentAttempt < Model
5
+ attr_accessor :id, :status, :id_at_gateway, :error_code, :error_text, :created_at, :modified_at
6
+ end
7
+
8
+ attr_accessor :id, :status, :amount, :gateway_account_id, :expires_at, :reference_id, :created_at,
9
+ :modified_at, :customer_id, :gateway, :active_payment_attempt
10
+
11
+ # OPERATIONS
12
+ #-----------
13
+
14
+ def self.create(params, env=nil, headers={})
15
+ Request.send('post', uri_path("payment_intents"), params, env, headers)
16
+ end
17
+
18
+ def self.update(id, params={}, env=nil, headers={})
19
+ Request.send('post', uri_path("payment_intents",id.to_s), params, env, headers)
20
+ end
21
+
22
+ def self.retrieve(id, env=nil, headers={})
23
+ Request.send('get', uri_path("payment_intents",id.to_s), {}, env, headers)
24
+ end
25
+
26
+ end # ~PaymentIntent
27
+ end # ~ChargeBee
@@ -0,0 +1,33 @@
1
+ module ChargeBee
2
+ class Plan < Model
3
+
4
+ attr_accessor :id, :name, :invoice_name, :description, :price, :period, :period_unit, :trial_period,
5
+ :trial_period_unit, :charge_model, :free_quantity, :setup_cost, :downgrade_penalty, :status,
6
+ :archived_at, :billing_cycles, :redirect_url, :enabled_in_hosted_pages, :enabled_in_portal,
7
+ :invoice_notes, :taxable, :meta_data
8
+
9
+ # OPERATIONS
10
+ #-----------
11
+
12
+ def self.create(params, env=nil, headers={})
13
+ Request.send('post', uri_path("plans"), params, env, headers)
14
+ end
15
+
16
+ def self.update(id, params={}, env=nil, headers={})
17
+ Request.send('post', uri_path("plans",id.to_s), params, env, headers)
18
+ end
19
+
20
+ def self.list(params={}, env=nil, headers={})
21
+ Request.send('get', uri_path("plans"), params, env, headers)
22
+ end
23
+
24
+ def self.retrieve(id, env=nil, headers={})
25
+ Request.send('get', uri_path("plans",id.to_s), {}, env, headers)
26
+ end
27
+
28
+ def self.delete(id, env=nil, headers={})
29
+ Request.send('post', uri_path("plans",id.to_s,"delete"), {}, env, headers)
30
+ end
31
+
32
+ end # ~Plan
33
+ end # ~ChargeBee
@@ -0,0 +1,31 @@
1
+ module ChargeBee
2
+ class PortalSession < Model
3
+
4
+ class LinkedCustomer < Model
5
+ attr_accessor :customer_id, :email, :has_billing_address, :has_payment_method, :has_active_subscription
6
+ end
7
+
8
+ attr_accessor :id, :token, :access_url, :redirect_url, :status, :created_at, :expires_at, :customer_id,
9
+ :login_at, :logout_at, :login_ipaddress, :logout_ipaddress, :linked_customers
10
+
11
+ # OPERATIONS
12
+ #-----------
13
+
14
+ def self.create(params, env=nil, headers={})
15
+ Request.send('post', uri_path("portal_sessions"), params, env, headers)
16
+ end
17
+
18
+ def self.retrieve(id, env=nil, headers={})
19
+ Request.send('get', uri_path("portal_sessions",id.to_s), {}, env, headers)
20
+ end
21
+
22
+ def self.logout(id, env=nil, headers={})
23
+ Request.send('post', uri_path("portal_sessions",id.to_s,"logout"), {}, env, headers)
24
+ end
25
+
26
+ def self.activate(id, params, env=nil, headers={})
27
+ Request.send('post', uri_path("portal_sessions",id.to_s,"activate"), params, env, headers)
28
+ end
29
+
30
+ end # ~PortalSession
31
+ end # ~ChargeBee
@@ -0,0 +1,86 @@
1
+ module ChargeBee
2
+ class Subscription < Model
3
+
4
+ class Addon < Model
5
+ attr_accessor :id, :quantity
6
+ end
7
+
8
+ class Coupon < Model
9
+ attr_accessor :coupon_id, :apply_till, :applied_count, :coupon_code
10
+ end
11
+
12
+ class ShippingAddress < Model
13
+ attr_accessor :first_name, :last_name, :email, :company, :phone, :line1, :line2, :line3, :city, :state_code, :state, :country, :zip
14
+ end
15
+
16
+ attr_accessor :id, :plan_id, :plan_quantity, :status, :start_date, :trial_start, :trial_end,
17
+ :current_term_start, :current_term_end, :remaining_billing_cycles, :po_number, :created_at,
18
+ :started_at, :activated_at, :cancelled_at, :cancel_reason, :affiliate_token, :created_from_ip,
19
+ :has_scheduled_changes, :due_invoices_count, :due_since, :total_dues, :addons, :coupon, :coupons,
20
+ :shipping_address, :invoice_notes, :meta_data
21
+
22
+ # OPERATIONS
23
+ #-----------
24
+
25
+ def self.create(params, env=nil, headers={})
26
+ Request.send('post', uri_path("subscriptions"), params, env, headers)
27
+ end
28
+
29
+ def self.create_for_customer(id, params, env=nil, headers={})
30
+ Request.send('post', uri_path("customers",id.to_s,"subscriptions"), params, env, headers)
31
+ end
32
+
33
+ def self.list(params={}, env=nil, headers={})
34
+ Request.send('get', uri_path("subscriptions"), params, env, headers)
35
+ end
36
+
37
+ def self.subscriptions_for_customer(id, params={}, env=nil, headers={})
38
+ Request.send('get', uri_path("customers",id.to_s,"subscriptions"), params, env, headers)
39
+ end
40
+
41
+ def self.retrieve(id, env=nil, headers={})
42
+ Request.send('get', uri_path("subscriptions",id.to_s), {}, env, headers)
43
+ end
44
+
45
+ def self.retrieve_with_scheduled_changes(id, env=nil, headers={})
46
+ Request.send('get', uri_path("subscriptions",id.to_s,"retrieve_with_scheduled_changes"), {}, env, headers)
47
+ end
48
+
49
+ def self.remove_scheduled_changes(id, env=nil, headers={})
50
+ Request.send('post', uri_path("subscriptions",id.to_s,"remove_scheduled_changes"), {}, env, headers)
51
+ end
52
+
53
+ def self.remove_scheduled_cancellation(id, params={}, env=nil, headers={})
54
+ Request.send('post', uri_path("subscriptions",id.to_s,"remove_scheduled_cancellation"), params, env, headers)
55
+ end
56
+
57
+ def self.update(id, params={}, env=nil, headers={})
58
+ Request.send('post', uri_path("subscriptions",id.to_s), params, env, headers)
59
+ end
60
+
61
+ def self.change_term_end(id, params, env=nil, headers={})
62
+ Request.send('post', uri_path("subscriptions",id.to_s,"change_term_end"), params, env, headers)
63
+ end
64
+
65
+ def self.cancel(id, params={}, env=nil, headers={})
66
+ Request.send('post', uri_path("subscriptions",id.to_s,"cancel"), params, env, headers)
67
+ end
68
+
69
+ def self.reactivate(id, params={}, env=nil, headers={})
70
+ Request.send('post', uri_path("subscriptions",id.to_s,"reactivate"), params, env, headers)
71
+ end
72
+
73
+ def self.add_charge_at_term_end(id, params, env=nil, headers={})
74
+ Request.send('post', uri_path("subscriptions",id.to_s,"add_charge_at_term_end"), params, env, headers)
75
+ end
76
+
77
+ def self.charge_addon_at_term_end(id, params, env=nil, headers={})
78
+ Request.send('post', uri_path("subscriptions",id.to_s,"charge_addon_at_term_end"), params, env, headers)
79
+ end
80
+
81
+ def self.delete(id, env=nil, headers={})
82
+ Request.send('post', uri_path("subscriptions",id.to_s,"delete"), {}, env, headers)
83
+ end
84
+
85
+ end # ~Subscription
86
+ end # ~ChargeBee
@@ -0,0 +1,45 @@
1
+ module ChargeBee
2
+ class Transaction < Model
3
+
4
+ class LinkedInvoice < Model
5
+ attr_accessor :invoice_id, :applied_amount, :applied_at, :invoice_date, :invoice_amount
6
+ end
7
+
8
+ class LinkedRefund < Model
9
+ attr_accessor :txn_id, :txn_status, :txn_date, :txn_amount
10
+ end
11
+
12
+ attr_accessor :id, :customer_id, :subscription_id, :payment_method, :reference_number, :gateway,
13
+ :description, :type, :date, :currency_code, :amount, :id_at_gateway, :status, :initiator_type,
14
+ :three_d_secure, :error_code, :error_text, :voided_at, :void_description, :amount_unused, :masked_card_number,
15
+ :reference_transaction_id, :refunded_txn_id, :reversal_transaction_id, :linked_invoices, :linked_refunds
16
+
17
+ # OPERATIONS
18
+ #-----------
19
+
20
+ def self.list(params={}, env=nil, headers={})
21
+ Request.send('get', uri_path("transactions"), params, env, headers)
22
+ end
23
+
24
+ def self.transactions_for_customer(id, params={}, env=nil, headers={})
25
+ Request.send('get', uri_path("customers",id.to_s,"transactions"), params, env, headers)
26
+ end
27
+
28
+ def self.transactions_for_subscription(id, params={}, env=nil, headers={})
29
+ Request.send('get', uri_path("subscriptions",id.to_s,"transactions"), params, env, headers)
30
+ end
31
+
32
+ def self.transactions_for_invoice(id, params={}, env=nil, headers={})
33
+ Request.send('get', uri_path("invoices",id.to_s,"transactions"), params, env, headers)
34
+ end
35
+
36
+ def self.retrieve(id, env=nil, headers={})
37
+ Request.send('get', uri_path("transactions",id.to_s), {}, env, headers)
38
+ end
39
+
40
+ def self.record_payment(id, params, env=nil, headers={})
41
+ Request.send('post', uri_path("invoices",id.to_s,"record_payment"), params, env, headers)
42
+ end
43
+
44
+ end # ~Transaction
45
+ end # ~ChargeBee
@@ -0,0 +1,16 @@
1
+ module ChargeBee
2
+ class Request
3
+
4
+ def self.send(method, url, params={}, env=nil, headers={})
5
+ env ||= ChargeBee.default_env
6
+ ser_params = Util.serialize(params)
7
+ resp = Rest.request(method, url, env, ser_params||={}, headers)
8
+ if resp.has_key?(:list)
9
+ ListResult.new(resp[:list], resp[:next_offset])
10
+ else
11
+ Result.new(resp)
12
+ end
13
+ end
14
+
15
+ end
16
+ end
@@ -0,0 +1,90 @@
1
+ require 'rest_client'
2
+ require 'json'
3
+
4
+ module ChargeBee
5
+ module Rest
6
+
7
+ def self.request(method, url, env, params=nil, headers)
8
+ raise Error.new('No environment configured.') unless env
9
+ api_key = env.api_key
10
+
11
+ if(ChargeBee.verify_ca_certs?)
12
+ ssl_opts = {
13
+ :verify_ssl => OpenSSL::SSL::VERIFY_PEER,
14
+ :ssl_ca_file => ChargeBee.ca_cert_path
15
+ }
16
+ else
17
+ ssl_opts = {
18
+ :verify_ssl => false
19
+ }
20
+ end
21
+ case method.to_s.downcase.to_sym
22
+ when :get, :head, :delete
23
+ headers = { :params => params }.merge(headers)
24
+ payload = nil
25
+ else
26
+ payload = params
27
+ end
28
+
29
+ user_agent = "Chargebee-Ruby-Client v#{ChargeBee::VERSION}"
30
+ headers = {
31
+ "User-Agent" => user_agent,
32
+ :accept => :json
33
+ }.merge(headers)
34
+ opts = {
35
+ :method => method,
36
+ :url => env.api_url(url),
37
+ :user => api_key,
38
+ :headers => headers,
39
+ :payload => payload,
40
+ :open_timeout => 50,
41
+ :timeout => 100
42
+ }.merge(ssl_opts)
43
+
44
+ begin
45
+ response = RestClient::Request.execute(opts)
46
+ rescue RestClient::ExceptionWithResponse => e
47
+ if rcode = e.http_code and rbody = e.http_body
48
+ raise handle_for_error(e, rcode, rbody)
49
+ else
50
+ raise IOError.new("IO Exception when trying to connect to chargebee with url #{opts[:url]} . Reason #{e}",e)
51
+ end
52
+ rescue Exception => e
53
+ raise IOError.new("IO Exception when trying to connect to chargebee with url #{opts[:url]} . Reason #{e}",e)
54
+ end
55
+ rbody = response.body
56
+ rcode = response.code
57
+ begin
58
+ resp = JSON.parse(rbody)
59
+ rescue Exception => e
60
+ raise Error.new("Response not in JSON format. Probably not a ChargeBee response \n #{rbody.inspect}",e)
61
+ end
62
+ resp = Util.symbolize_keys(resp)
63
+ resp
64
+ end
65
+
66
+ def self.handle_for_error(e, rcode=nil, rbody=nil)
67
+ if(rcode == 204)
68
+ raise Error.new("No response returned by the chargebee api. The http status code is #{rcode}")
69
+ end
70
+ begin
71
+ error_obj = JSON.parse(rbody)
72
+ error_obj = Util.symbolize_keys(error_obj)
73
+ rescue Exception => e
74
+ raise Error.new("Error response not in JSON format. The http status code is #{rcode} \n #{rbody.inspect}",e)
75
+ end
76
+ type = error_obj[:type]
77
+ if("payment" == type)
78
+ raise PaymentError.new(rcode, error_obj)
79
+ elsif("operation_failed" == type)
80
+ raise OperationFailedError.new(rcode, error_obj)
81
+ elsif("invalid_request" == type)
82
+ raise InvalidRequestError.new(rcode, error_obj)
83
+ else
84
+ raise APIError.new(rcode, error_obj)
85
+ end
86
+
87
+ end
88
+
89
+ end
90
+ end
@@ -0,0 +1,100 @@
1
+ module ChargeBee
2
+ class Result
3
+
4
+ def initialize(response)
5
+ @response = response
6
+ end
7
+
8
+ def subscription()
9
+ get(:subscription, Subscription,
10
+ {:addons => Subscription::Addon, :coupons => Subscription::Coupon, :shipping_address => Subscription::ShippingAddress});
11
+ end
12
+
13
+ def customer()
14
+ get(:customer, Customer,
15
+ {:billing_address => Customer::BillingAddress, :contacts => Customer::Contact, :payment_method => Customer::PaymentMethod});
16
+ end
17
+
18
+ def card()
19
+ get(:card, Card);
20
+ end
21
+
22
+ def invoice()
23
+ get(:invoice, Invoice,
24
+ {:line_items => Invoice::LineItem, :discounts => Invoice::Discount, :taxes => Invoice::Tax, :linked_transactions => Invoice::LinkedTransaction, :linked_orders => Invoice::LinkedOrder, :notes => Invoice::Note, :shipping_address => Invoice::ShippingAddress, :billing_address => Invoice::BillingAddress});
25
+ end
26
+
27
+ def order()
28
+ get(:order, Order);
29
+ end
30
+
31
+ def transaction()
32
+ get(:transaction, Transaction,
33
+ {:linked_invoices => Transaction::LinkedInvoice, :linked_refunds => Transaction::LinkedRefund});
34
+ end
35
+
36
+ def hosted_page()
37
+ get(:hosted_page, HostedPage);
38
+ end
39
+
40
+ def estimate()
41
+ get(:estimate, Estimate,
42
+ {:line_items => Estimate::LineItem, :discounts => Estimate::Discount, :taxes => Estimate::Tax});
43
+ end
44
+
45
+ def plan()
46
+ get(:plan, Plan);
47
+ end
48
+
49
+ def addon()
50
+ get(:addon, Addon);
51
+ end
52
+
53
+ def coupon()
54
+ get(:coupon, Coupon);
55
+ end
56
+
57
+ def coupon_code()
58
+ get(:coupon_code, CouponCode);
59
+ end
60
+
61
+ def address()
62
+ get(:address, Address);
63
+ end
64
+
65
+ def event()
66
+ get(:event, Event,
67
+ {:webhooks => Event::Webhook});
68
+ end
69
+
70
+ def comment()
71
+ get(:comment, Comment);
72
+ end
73
+
74
+ def download()
75
+ get(:download, Download);
76
+ end
77
+
78
+ def portal_session()
79
+ get(:portal_session, PortalSession,
80
+ {:linked_customers => PortalSession::LinkedCustomer});
81
+ end
82
+
83
+ def payment_intent()
84
+ get(:payment_intent, PaymentIntent,
85
+ {:payment_attempt => PaymentIntent::PaymentAttempt});
86
+ end
87
+
88
+
89
+
90
+ private
91
+ def get(type, klass, sub_types = {})
92
+ klass.construct(@response[type], sub_types)
93
+ end
94
+
95
+ def to_s(*args)
96
+ JSON.pretty_generate(@response)
97
+ end
98
+
99
+ end
100
+ end