aptible-billforward 0.0.1

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.
checksums.yaml ADDED
@@ -0,0 +1,7 @@
1
+ ---
2
+ SHA1:
3
+ metadata.gz: ea59a53fe3a5a639a6262239b4b467048239a932
4
+ data.tar.gz: 77e5113ccd920ae240202308ef5cbd66b4b50026
5
+ SHA512:
6
+ metadata.gz: dedbbc99b242c9396376ef559fff7d48c01793a63fe7fb9bcfca0f7557f9b2d44a99724b9fb2d70784aa2a769fe4f25f4770c21e7019b02d7ee1f2bfdc39f129
7
+ data.tar.gz: 8de82401b7c813315a149c8d6e927c55b2108d05bd1945d7115bb08e6d1fd1632134530e6fa7e6b7e0069909e76b391534e0639dedadbbc2d12d9b40d388e1cc
data/.gitignore ADDED
@@ -0,0 +1,17 @@
1
+ *.gem
2
+ *.rbc
3
+ .bundle
4
+ .config
5
+ .yardoc
6
+ Gemfile.lock
7
+ InstalledFiles
8
+ _yardoc
9
+ coverage
10
+ doc/
11
+ lib/bundler/man
12
+ pkg
13
+ rdoc
14
+ spec/reports
15
+ test/tmp
16
+ test/version_tmp
17
+ tmp
data/.rspec ADDED
@@ -0,0 +1,2 @@
1
+ --color
2
+ --format documentation
data/Gemfile ADDED
@@ -0,0 +1,4 @@
1
+ source 'https://rubygems.org'
2
+
3
+ # Specify your gem's dependencies in aptible-auth.gemspec
4
+ gemspec
data/LICENSE.md ADDED
@@ -0,0 +1,22 @@
1
+ Copyright (c) 2013 Aptible, Inc.
2
+
3
+ MIT License
4
+
5
+ Permission is hereby granted, free of charge, to any person obtaining
6
+ a copy of this software and associated documentation files (the
7
+ "Software"), to deal in the Software without restriction, including
8
+ without limitation the rights to use, copy, modify, merge, publish,
9
+ distribute, sublicense, and/or sell copies of the Software, and to
10
+ permit persons to whom the Software is furnished to do so, subject to
11
+ the following conditions:
12
+
13
+ The above copyright notice and this permission notice shall be
14
+ included in all copies or substantial portions of the Software.
15
+
16
+ THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
17
+ EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
18
+ MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
19
+ NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
20
+ LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
21
+ OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
22
+ WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
data/Procfile ADDED
@@ -0,0 +1 @@
1
+ console: bundle exec pry -r aptible/billforward
data/README.md ADDED
@@ -0,0 +1,4 @@
1
+ aptible-bf-ruby
2
+ ===============
3
+
4
+ Ruby client for BillForward
data/Rakefile ADDED
@@ -0,0 +1,4 @@
1
+ require 'bundler/gem_tasks'
2
+
3
+ require 'aptible/tasks'
4
+ Aptible::Tasks.load_tasks
@@ -0,0 +1,28 @@
1
+ # encoding: utf-8
2
+ lib = File.expand_path('../lib', __FILE__)
3
+ $LOAD_PATH.unshift(lib) unless $LOAD_PATH.include?(lib)
4
+
5
+ require 'English'
6
+ require 'aptible/billforward/version'
7
+
8
+ Gem::Specification.new do |spec|
9
+ spec.name = 'aptible-billforward'
10
+ spec.version = Aptible::BillForward::VERSION
11
+ spec.authors = ['Skylar Anderson']
12
+ spec.email = ['skylar@aptible.com']
13
+ spec.description = 'Ruby client for BillForward.net'
14
+ spec.summary = 'Ruby client for BillForward.net'
15
+ spec.homepage = 'https://github.com/aptible/aptible-bf-ruby'
16
+ spec.license = 'MIT'
17
+
18
+ spec.files = `git ls-files`.split($RS)
19
+ spec.test_files = spec.files.grep(/^spec\//)
20
+ spec.require_paths = ['lib']
21
+
22
+ spec.add_dependency 'gem_config'
23
+ spec.add_dependency 'sawyer', '~> 0.5.3'
24
+
25
+ spec.add_development_dependency 'bundler', '~> 1.3'
26
+ spec.add_development_dependency 'aptible-tasks'
27
+ spec.add_development_dependency 'rake'
28
+ end
@@ -0,0 +1,55 @@
1
+ require 'sawyer'
2
+ require 'aptible/billforward/serializer'
3
+
4
+ module Aptible
5
+ module BillForward
6
+ class Client
7
+ include BillForward::Defaults
8
+ attr_reader :agent
9
+ attr_reader :last_response
10
+
11
+ def get(url, query = {})
12
+ request :get, url, nil, query: query
13
+ end
14
+
15
+ def post(url, resource, query = {})
16
+ request(:post, url, resource, query: query).first
17
+ end
18
+
19
+ def put(url, resource, query = {})
20
+ request :put, url, resource, query: query
21
+ end
22
+
23
+ def patch(url, resource, query = {})
24
+ request :patch, url, resource, query: query
25
+ end
26
+
27
+ def agent
28
+ @agent ||= Sawyer::Agent.new(api_endpoint, sawyer_options) do |http|
29
+ http.headers[:accept] = media_type
30
+ http.headers[:user_agent] = user_agent
31
+ http.headers[:authorization] = "Bearer #{access_token}"
32
+ end
33
+ end
34
+
35
+ private
36
+
37
+ def sawyer_options
38
+ {
39
+ faraday: Faraday.new(connection_options),
40
+ serializer: Aptible::BillForward::Serializer.any_json
41
+ }
42
+ end
43
+
44
+ def request(method, path, data, options = {})
45
+ options[:headers] ||= {}
46
+ unless method == :get
47
+ options[:headers][:content_type] = 'application/json'
48
+ end
49
+
50
+ @last_response = agent.call(method, path, data, options)
51
+ @last_response.data
52
+ end
53
+ end
54
+ end
55
+ end
@@ -0,0 +1,30 @@
1
+ module Aptible
2
+ module BillForward
3
+ module Defaults
4
+ def access_token
5
+ Aptible::BillForward.configuration.access_token
6
+ end
7
+
8
+ def api_endpoint
9
+ Aptible::BillForward.configuration.root_url
10
+ end
11
+
12
+ def user_agent
13
+ "aptible-billforward Ruby Gem #{Aptible::BillForward::VERSION}"
14
+ end
15
+
16
+ def media_type
17
+ 'application/json'
18
+ end
19
+
20
+ def connection_options
21
+ {
22
+ headers: {
23
+ accept: media_type,
24
+ user_agent: user_agent
25
+ }
26
+ }
27
+ end
28
+ end
29
+ end
30
+ end
@@ -0,0 +1,33 @@
1
+ module Aptible
2
+ module BillForward
3
+ class Exception < ::StandardError
4
+ attr_accessor :cause
5
+
6
+ def initialize(message, attrs = {})
7
+ self.cause = attrs[:cause]
8
+ super(message)
9
+ end
10
+ end
11
+
12
+ class ResponseError < Exception
13
+ attr_accessor :response
14
+ attr_accessor :body
15
+
16
+ def initialize(message, attrs = {})
17
+ self.response = attrs[:response]
18
+ self.body = attrs[:body]
19
+
20
+ if body.present? && body.key?(:errorMessage)
21
+ error = body[:errorMessage]
22
+ message = "#{message} (#{error})"
23
+ elsif response
24
+ message = "#{message} (\"#{response.inspect}\")"
25
+ end
26
+
27
+ super(message, attrs)
28
+ end
29
+ end
30
+
31
+ class ResourceNotFoundError < ResponseError; end
32
+ end
33
+ end
@@ -0,0 +1,39 @@
1
+ module Aptible
2
+ module BillForward
3
+ class Account < Resource
4
+ def serialize
5
+ to_attrs
6
+ end
7
+
8
+ def create_payment_method(params)
9
+ Aptible::BillForward::PaymentMethod.create(
10
+ params.merge(accountID: id)
11
+ )
12
+ end
13
+
14
+ def create_subscription(params)
15
+ Aptible::BillForward::Subscription.create(
16
+ params.merge(accountID: id)
17
+ )
18
+ end
19
+
20
+ def payment_methods(params = {})
21
+ Aptible::BillForward::PaymentMethod.by_account_id(id, params)
22
+ end
23
+
24
+ def subscriptions(params = {})
25
+ Aptible::BillForward::Subscription.by_account_id(id, params)
26
+ end
27
+
28
+ def bootstrap_active_subscription(params)
29
+ subscription = create_subscription params.slice(:productRatePlanID)
30
+ payment_method = Aptible::BillForward::PaymentMethod.find(
31
+ params[:payment_method_id]
32
+ )
33
+
34
+ subscription.link_payment_method payment_method
35
+ subscription.update(state: 'AwaitingPayment')
36
+ end
37
+ end
38
+ end
39
+ end
@@ -0,0 +1,6 @@
1
+ module Aptible
2
+ module BillForward
3
+ class Invoice < Resource
4
+ end
5
+ end
6
+ end
@@ -0,0 +1,17 @@
1
+ module Aptible
2
+ module BillForward
3
+ class PaymentMethod < Resource
4
+ def self.basename
5
+ 'payment-methods'
6
+ end
7
+
8
+ def serialize
9
+ to_attrs
10
+ end
11
+
12
+ def self.by_account_id(account_id, params = {})
13
+ client.get "#{collection_path}/account/#{account_id}", params
14
+ end
15
+ end
16
+ end
17
+ end
@@ -0,0 +1,9 @@
1
+ module Aptible
2
+ module BillForward
3
+ class PaymentMethodSubscriptionLink < Resource
4
+ def serialize
5
+ to_attrs
6
+ end
7
+ end
8
+ end
9
+ end
@@ -0,0 +1,17 @@
1
+ module Aptible
2
+ module BillForward
3
+ class ProductRatePlan < Resource
4
+ def self.basename
5
+ 'product-rate-plans'
6
+ end
7
+
8
+ def serialize
9
+ to_attrs
10
+ end
11
+
12
+ def self.by_account_id(account_id, params = {})
13
+ client.get "#{collection_path}/account/#{account_id}", params
14
+ end
15
+ end
16
+ end
17
+ end
@@ -0,0 +1,45 @@
1
+ module Aptible
2
+ module BillForward
3
+ class Subscription < Resource
4
+ def serialize
5
+ to_attrs
6
+ end
7
+
8
+ def usage_periods(_params = {})
9
+ @usage_periods ||=
10
+ Aptible::BillForward::UsagePeriod.by_subscription_id(id)
11
+ end
12
+
13
+ def usage_sessions(_params = {})
14
+ @usage_sessions ||=
15
+ Aptible::BillForward::UsageSession.by_subscription_id(id)
16
+ end
17
+
18
+ def usage(_params = {})
19
+ @usage ||= Aptible::BillForward::Usage.by_subscription_id(id)
20
+ end
21
+
22
+ def create_usage_session(params = {})
23
+ usage_params = params.merge(
24
+ subscriptionID: id,
25
+ sessionID: Aptible::BillForward::UsageSession.generate_session_id
26
+ )
27
+ Aptible::BillForward::UsageSession.create(usage_params)
28
+ end
29
+
30
+ def link_payment_method(payment_method)
31
+ Aptible::BillForward::PaymentMethodSubscriptionLink.create(
32
+ subscriptionID: id, paymentMethodID: payment_method.id
33
+ )
34
+ end
35
+
36
+ def self.by_account_id(account_id, params = {})
37
+ client.get "#{collection_path}/account/#{account_id}", params
38
+ end
39
+
40
+ def href
41
+ "#{self.class.collection_path}"
42
+ end
43
+ end
44
+ end
45
+ end
@@ -0,0 +1,9 @@
1
+ module Aptible
2
+ module BillForward
3
+ class UnitOfMeasure < Resource
4
+ def self.basename
5
+ 'units-of-measure'
6
+ end
7
+ end
8
+ end
9
+ end
@@ -0,0 +1,13 @@
1
+ module Aptible
2
+ module BillForward
3
+ class Usage < Resource
4
+ def self.basename
5
+ 'usage'
6
+ end
7
+
8
+ def self.create(params)
9
+ client.post "#{collection_path}/create", new(client.agent, params)
10
+ end
11
+ end
12
+ end
13
+ end
@@ -0,0 +1,6 @@
1
+ module Aptible
2
+ module BillForward
3
+ class UsagePeriod < Resource
4
+ end
5
+ end
6
+ end
@@ -0,0 +1,32 @@
1
+ require 'securerandom'
2
+
3
+ module Aptible
4
+ module BillForward
5
+ class UsageSession < Resource
6
+ def self.find(subscriptionID, sessionID)
7
+ by_subscription_id(subscriptionID).find do |session|
8
+ session.sessionID == sessionID
9
+ end
10
+ end
11
+
12
+ def self.create(params)
13
+ client.post "#{collection_path}/start", new(client.agent, params)
14
+ end
15
+
16
+ def self.stop(params)
17
+ client.post "#{collection_path}/stop", new(client.agent, params)
18
+ end
19
+
20
+ def self.generate_session_id
21
+ SecureRandom.uuid
22
+ end
23
+
24
+ def create_usage(usage_params)
25
+ usage = usage_params.merge(
26
+ to_attrs.slice(:organizationID, :subscriptionID, :sessionID, :uom)
27
+ )
28
+ Aptible::BillForward::Usage.create usage
29
+ end
30
+ end
31
+ end
32
+ end
@@ -0,0 +1,80 @@
1
+ require 'aptible/billforward/response'
2
+
3
+ module Aptible
4
+ module BillForward
5
+ class Resource < Sawyer::Resource
6
+ def self.all(query = {})
7
+ client.get collection_path, query: query
8
+ end
9
+
10
+ def self.find(id)
11
+ client.get("#{collection_path}/#{id}").first
12
+ end
13
+
14
+ def self.create(params, query = {})
15
+ client.post collection_path, new(client.agent, params), query: query
16
+ end
17
+
18
+ def self.collection_path
19
+ basename
20
+ end
21
+
22
+ def update(params)
23
+ self.attrs = attrs.merge(params)
24
+ client.put href, self
25
+ end
26
+
27
+ def href
28
+ "#{self.class.collection_path}/#{id}"
29
+ end
30
+
31
+ def self.basename
32
+ name.split('::').last.underscore.dasherize.pluralize
33
+ end
34
+
35
+ def self.client
36
+ @client ||= Aptible::BillForward::Client.new
37
+ end
38
+
39
+ def client
40
+ @client ||= Aptible::BillForward::Client.new
41
+ end
42
+
43
+ def invoice
44
+ return nil unless invoiceID
45
+ Aptible::BillForward::Invoice.find(invoiceID)
46
+ end
47
+
48
+ def subscription
49
+ return nil unless subscriptionID
50
+ Aptible::BillForward::Subscription.find(subscriptionID)
51
+ end
52
+
53
+ def self.by_subscription_id(subscription_id, options = {})
54
+ state = options[:active] ? '/active' : ''
55
+ client.get(
56
+ "#{collection_path}/#{subscription_id}#{state}",
57
+ order: 'DESC', order_by: 'start'
58
+ )
59
+ end
60
+
61
+ def serialize
62
+ type = self.class.basename.underscore.camelize(:lower).pluralize
63
+ body = {}
64
+ body[type] = [to_attrs]
65
+ body
66
+ end
67
+ end
68
+ end
69
+ end
70
+
71
+ require 'aptible/billforward/resource/account'
72
+ require 'aptible/billforward/resource/invoice'
73
+ require 'aptible/billforward/resource/payment_method'
74
+ require 'aptible/billforward/resource/payment_method_subscription_link'
75
+ require 'aptible/billforward/resource/product_rate_plan'
76
+ require 'aptible/billforward/resource/subscription'
77
+ require 'aptible/billforward/resource/usage'
78
+ require 'aptible/billforward/resource/units_of_measure'
79
+ require 'aptible/billforward/resource/usage_period'
80
+ require 'aptible/billforward/resource/usage_session'
@@ -0,0 +1,45 @@
1
+ require 'logger'
2
+ require 'aptible/billforward/exceptions'
3
+
4
+ module Sawyer
5
+ class Response
6
+ # rubocop:disable MethodLength
7
+ def initialize(agent, res, options = {})
8
+ fail Aptible::BillForward::ResponseError.new(
9
+ @status.to_s,
10
+ response: @res,
11
+ body: @data,
12
+ cause: @status
13
+ ) if res.status >= 400
14
+
15
+ @res = res
16
+ @agent = agent
17
+ @status = res.status
18
+ @headers = res.headers
19
+ @env = res.env
20
+ @rels = process_rels
21
+ @started = options[:sawyer_started]
22
+ @ended = options[:sawyer_ended]
23
+ @data = if @headers[:content_type] =~ /json|msgpack/
24
+ process_data(@agent.decode_body(res.body))
25
+ else
26
+ res.body
27
+ end
28
+ end
29
+ # rubocop:enable MethodLength
30
+
31
+ def process_data(data)
32
+ data = data[:results] if data.key? :results
33
+ case data
34
+ when Hash then klass_from_type(data).new(agent, data)
35
+ when Array then data.map { |hash| process_data(hash) }
36
+ when nil then nil
37
+ else data
38
+ end
39
+ end
40
+
41
+ def klass_from_type(result)
42
+ "Aptible::BillForward::#{result[:@type].classify}".constantize
43
+ end
44
+ end
45
+ end
@@ -0,0 +1,20 @@
1
+ module Aptible
2
+ module BillForward
3
+ class Serializer < Sawyer::Serializer
4
+ def encode_object(resource)
5
+ return resource.serialize if resource.respond_to? :serialize
6
+ case resource
7
+ when Hash then encode_hash(resource)
8
+ when Array then resource.map { |o| encode_object(o) }
9
+ else resource
10
+ end
11
+ end
12
+
13
+ def time_field?(key, value)
14
+ time_fields = %w(created updated start stop initalPeriodStart
15
+ currentPeriodStart currentPeriodEnd)
16
+ value && time_fields.include?(key)
17
+ end
18
+ end
19
+ end
20
+ end
@@ -0,0 +1,5 @@
1
+ module Aptible
2
+ module BillForward
3
+ VERSION = '0.0.1'
4
+ end
5
+ end
@@ -0,0 +1,21 @@
1
+ require 'gem_config'
2
+ require 'aptible/billforward/defaults'
3
+
4
+ module Aptible
5
+ module BillForward
6
+ include GemConfig::Base
7
+
8
+ with_configuration do
9
+ has :root_url,
10
+ classes: String,
11
+ default: ENV['BILLFORWARD_ROOT_URL'] || 'https://api.billforward.net'
12
+
13
+ has :access_token,
14
+ classes: String,
15
+ default: ENV['BILLFORWARD_ACCESS_TOKEN'] || ''
16
+ end
17
+ end
18
+ end
19
+
20
+ require 'aptible/billforward/client'
21
+ require 'aptible/billforward/resource'
metadata ADDED
@@ -0,0 +1,140 @@
1
+ --- !ruby/object:Gem::Specification
2
+ name: aptible-billforward
3
+ version: !ruby/object:Gem::Version
4
+ version: 0.0.1
5
+ platform: ruby
6
+ authors:
7
+ - Skylar Anderson
8
+ autorequire:
9
+ bindir: bin
10
+ cert_chain: []
11
+ date: 2014-09-23 00:00:00.000000000 Z
12
+ dependencies:
13
+ - !ruby/object:Gem::Dependency
14
+ name: gem_config
15
+ requirement: !ruby/object:Gem::Requirement
16
+ requirements:
17
+ - - '>='
18
+ - !ruby/object:Gem::Version
19
+ version: '0'
20
+ type: :runtime
21
+ prerelease: false
22
+ version_requirements: !ruby/object:Gem::Requirement
23
+ requirements:
24
+ - - '>='
25
+ - !ruby/object:Gem::Version
26
+ version: '0'
27
+ - !ruby/object:Gem::Dependency
28
+ name: sawyer
29
+ requirement: !ruby/object:Gem::Requirement
30
+ requirements:
31
+ - - ~>
32
+ - !ruby/object:Gem::Version
33
+ version: 0.5.3
34
+ type: :runtime
35
+ prerelease: false
36
+ version_requirements: !ruby/object:Gem::Requirement
37
+ requirements:
38
+ - - ~>
39
+ - !ruby/object:Gem::Version
40
+ version: 0.5.3
41
+ - !ruby/object:Gem::Dependency
42
+ name: bundler
43
+ requirement: !ruby/object:Gem::Requirement
44
+ requirements:
45
+ - - ~>
46
+ - !ruby/object:Gem::Version
47
+ version: '1.3'
48
+ type: :development
49
+ prerelease: false
50
+ version_requirements: !ruby/object:Gem::Requirement
51
+ requirements:
52
+ - - ~>
53
+ - !ruby/object:Gem::Version
54
+ version: '1.3'
55
+ - !ruby/object:Gem::Dependency
56
+ name: aptible-tasks
57
+ requirement: !ruby/object:Gem::Requirement
58
+ requirements:
59
+ - - '>='
60
+ - !ruby/object:Gem::Version
61
+ version: '0'
62
+ type: :development
63
+ prerelease: false
64
+ version_requirements: !ruby/object:Gem::Requirement
65
+ requirements:
66
+ - - '>='
67
+ - !ruby/object:Gem::Version
68
+ version: '0'
69
+ - !ruby/object:Gem::Dependency
70
+ name: rake
71
+ requirement: !ruby/object:Gem::Requirement
72
+ requirements:
73
+ - - '>='
74
+ - !ruby/object:Gem::Version
75
+ version: '0'
76
+ type: :development
77
+ prerelease: false
78
+ version_requirements: !ruby/object:Gem::Requirement
79
+ requirements:
80
+ - - '>='
81
+ - !ruby/object:Gem::Version
82
+ version: '0'
83
+ description: Ruby client for BillForward.net
84
+ email:
85
+ - skylar@aptible.com
86
+ executables: []
87
+ extensions: []
88
+ extra_rdoc_files: []
89
+ files:
90
+ - .gitignore
91
+ - .rspec
92
+ - Gemfile
93
+ - LICENSE.md
94
+ - Procfile
95
+ - README.md
96
+ - Rakefile
97
+ - aptible-billforward.gemspec
98
+ - lib/aptible/billforward.rb
99
+ - lib/aptible/billforward/client.rb
100
+ - lib/aptible/billforward/defaults.rb
101
+ - lib/aptible/billforward/exceptions.rb
102
+ - lib/aptible/billforward/resource.rb
103
+ - lib/aptible/billforward/resource/account.rb
104
+ - lib/aptible/billforward/resource/invoice.rb
105
+ - lib/aptible/billforward/resource/payment_method.rb
106
+ - lib/aptible/billforward/resource/payment_method_subscription_link.rb
107
+ - lib/aptible/billforward/resource/product_rate_plan.rb
108
+ - lib/aptible/billforward/resource/subscription.rb
109
+ - lib/aptible/billforward/resource/units_of_measure.rb
110
+ - lib/aptible/billforward/resource/usage.rb
111
+ - lib/aptible/billforward/resource/usage_period.rb
112
+ - lib/aptible/billforward/resource/usage_session.rb
113
+ - lib/aptible/billforward/response.rb
114
+ - lib/aptible/billforward/serializer.rb
115
+ - lib/aptible/billforward/version.rb
116
+ homepage: https://github.com/aptible/aptible-bf-ruby
117
+ licenses:
118
+ - MIT
119
+ metadata: {}
120
+ post_install_message:
121
+ rdoc_options: []
122
+ require_paths:
123
+ - lib
124
+ required_ruby_version: !ruby/object:Gem::Requirement
125
+ requirements:
126
+ - - '>='
127
+ - !ruby/object:Gem::Version
128
+ version: '0'
129
+ required_rubygems_version: !ruby/object:Gem::Requirement
130
+ requirements:
131
+ - - '>='
132
+ - !ruby/object:Gem::Version
133
+ version: '0'
134
+ requirements: []
135
+ rubyforge_project:
136
+ rubygems_version: 2.2.2
137
+ signing_key:
138
+ specification_version: 4
139
+ summary: Ruby client for BillForward.net
140
+ test_files: []