infusionsoft 1.0.2

Sign up to get free protection for your applications and to get access to all the features.
@@ -0,0 +1,5 @@
1
+ *.gem
2
+ log/*.log
3
+ tmp/**/*
4
+ .DS_Store
5
+ rdoc/
@@ -0,0 +1,21 @@
1
+ Copyright (c) 2011 Nathan Leavitt & Infused Systems
2
+
3
+ Permission is hereby granted, free of charge, to any person obtaining
4
+ a copy of this software and associated documentation files (the
5
+ "Software"), to deal in the Software without restriction, including
6
+ without limitation the rights to use, copy, modify, merge, publish,
7
+ distribute, sublicense, and/or sell copies of the Software, and to
8
+ permit persons to whom the Software is furnished to do so, subject to
9
+ the following conditions:
10
+
11
+ The above copyright notice and this permission notice shall be
12
+ included in all copies or substantial portions of the Software.
13
+
14
+ THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
15
+ EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
16
+ MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
17
+ NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
18
+ LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
19
+ OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
20
+ WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
21
+
@@ -0,0 +1,100 @@
1
+ # The Infusionsoft Ruby Gem
2
+ A Ruby wrapper for the Infusionsoft API
3
+
4
+ ## <a name="installation">Installation</a>
5
+ gem install infusionsoft
6
+
7
+ ## <a name="documentation">Documentation</a>
8
+ documentation link here
9
+
10
+ ## <a name="setup">Setup & Configuration</a>
11
+ For Rails, create an initilizer in `config\initilizers` called infusionsoft.rb and the following
12
+
13
+ Infusionsoft.configure do |config|
14
+ config.api_url = 'YOUR_INFUSIONSOFT_URL' # example infused.infusionsoft.com
15
+ config.api_key = 'YOUR_INFUSIONSOFT_API_KEY'
16
+ end
17
+
18
+ ## <a name="examples">Usage Examples</a>
19
+
20
+ # Get a users first and last name using the DataService
21
+ Infusionsoft.data_load('Contact', contact_id, [:FirstName, :LastName])
22
+
23
+ # Update a contact with specific field values
24
+ Infusionsoft.contact_upudate(contact_id, { :FirstName => 'first_name', :Email => 'test@test.com' })
25
+
26
+ # Add a new Contact
27
+ Infusionsoft.contact_add({:FirstName => 'first_name', :LastName => 'last_name', :Email => 'test@test.com'})
28
+
29
+ # Create a blank Invoice
30
+ invoice_id = Infusionsoft.invoice_create_blank_order(contact_id, description, Date.today, lead_affiliate_id, sale_affiliate_id)
31
+
32
+ # Then add item to invoice
33
+ Infusionsoft.invoice_add_order_item(invoice_id, product_id, product_type, amount, quantity, description_here, notes)
34
+
35
+ # Then charge the invoice
36
+ Infusionsoft.invoice_charge_invoice(invoice_id, notes, credit_card_id, merchange_id, bypass_commissions)
37
+
38
+
39
+ ## <a name="contributing">Contributing</a>
40
+ In the spirit of [free software](http://www.fsf.org/licensing/essays/free-sw.html), **everyone** is encouraged to help improve this project.
41
+
42
+ Here are some ways *you* can contribute:
43
+
44
+ * by using alpha, beta, and prerelease versions
45
+ * by reporting bugs
46
+ * by suggesting new features
47
+ * by writing or editing documentation
48
+ * by writing specifications
49
+ * by writing code (**no patch is too small**: fix typos, add comments, clean up inconsistent whitespace)
50
+ * by refactoring code
51
+ * by closing [issues](https://github.com/nateleavitt/infusionsoft/issues)
52
+ * by reviewing patches
53
+
54
+ ## <a name="issues">Submitting an Issue</a>
55
+ We use the [GitHub issue tracker](https://github.com/nateleavitt/infusionsoft/issues) to track bugs and
56
+ features. Before submitting a bug report or feature request, check to make sure it hasn't already
57
+ been submitted. You can indicate support for an existing issuse by voting it up. When submitting a
58
+ bug report, please include a [Gist](https://gist.github.com/) that includes a stack trace and any
59
+ details that may be necessary to reproduce the bug, including your gem version, Ruby version, and
60
+ operating system. Ideally, a bug report should include a pull request with failing specs.
61
+
62
+ ## <a name="pulls">Submitting a Pull Request</a>
63
+ 1. Fork the project.
64
+ 2. Create a topic branch.
65
+ 3. Implement your feature or bug fix.
66
+ 4. Add documentation for your feature or bug fix.
67
+ 5. Run <tt>bundle exec rake doc:yard</tt>. If your changes are not 100% documented, go back to step 4.
68
+ 6. Add specs for your feature or bug fix.
69
+ 7. Run <tt>bundle exec rake spec</tt>. If your changes are not 100% covered, go back to step 6.
70
+ 8. Commit and push your changes.
71
+ 9. Submit a pull request. Please do not include changes to the gemspec, version, or history file. (If you want to create your own version for some reason, please do so in a separate commit.)
72
+
73
+ ## <a name="rubies">Supported Rubies</a>
74
+ This library aims to support the following Ruby implementations:
75
+
76
+ * Ruby 1.8.7
77
+ * Ruby 1.9.1
78
+ * Ruby 1.9.2
79
+ * [JRuby](http://www.jruby.org/)
80
+ * [Rubinius](http://rubini.us/)
81
+ * [Ruby Enterprise Edition](http://www.rubyenterpriseedition.com/)
82
+
83
+ If something doesn't work on one of these interpreters, it should be considered
84
+ a bug.
85
+
86
+ This library may inadvertently work (or seem to work) on other Ruby
87
+ implementations, however support will only be provided for the versions listed
88
+ above.
89
+
90
+ If you would like this library to support another Ruby version, you may
91
+ volunteer to be a maintainer. Being a maintainer entails making sure all tests
92
+ run and pass on that implementation. When something breaks on your
93
+ implementation, you will be personally responsible for providing patches in a
94
+ timely fashion. If critical issues for a particular implementation exist at the
95
+ time of a major release, support for that Ruby version may be dropped.
96
+
97
+ ## <a name="copyright">Copyright</a>
98
+ Copyright (c) 2011 Nathan Leavitt & Infused Systems
99
+ See [LICENSE](https://github.com/nateleavitt/infusionsoft/blob/master/LICENSE.md) for details.
100
+
@@ -0,0 +1,18 @@
1
+ # encoding: utf-8
2
+ require File.expand_path('../lib/infusionsoft/version', __FILE__)
3
+
4
+ Gem::Specification.new do |gem|
5
+ gem.name = 'infusionsoft'
6
+ gem.summary = %q{Ruby wrapper for the Infusionsoft API}
7
+ gem.description = 'A Ruby wrapper written for the Infusionsoft API'
8
+ gem.authors = ["Nathan Leavitt"]
9
+ gem.email = ['nate@infusedsystems.com']
10
+ gem.executables = `git ls-files -- bin/*`.split("\n").map{|f| File.basename(f)}
11
+ gem.files = `git ls-files`.split("\n")
12
+ gem.homepage = 'https://github.com/nateleavitt/infusionsoft'
13
+ gem.require_paths = ['lib']
14
+ gem.required_rubygems_version = Gem::Requirement.new('>= 1.3.6')
15
+
16
+ gem.version = Infusionsoft::VERSION.dup
17
+ end
18
+
@@ -0,0 +1,27 @@
1
+ require 'infusionsoft/api'
2
+ require 'infusionsoft/client'
3
+ require 'infusionsoft/configuration'
4
+ #require 'api_infusionsoft/error'
5
+
6
+ module Infusionsoft
7
+ extend Configuration
8
+ class << self
9
+ # Alias for Infusionsoft::Client.new
10
+ #
11
+ # @return [Infusionsoft::Client]
12
+ def new(options={})
13
+ Infusionsoft::Client.new(options)
14
+ end
15
+
16
+ # Delegate to ApiInfusionsoft::Client
17
+ def method_missing(method, *args, &block)
18
+ return super unless new.respond_to?(method)
19
+ new.send(method, *args, &block)
20
+ end
21
+
22
+ def respond_to?(method, include_private = false)
23
+ new.respond_to?(method, include_private) || super(method, include_private)
24
+ end
25
+ end
26
+ end
27
+
@@ -0,0 +1,22 @@
1
+ require 'infusionsoft/configuration'
2
+ require 'infusionsoft/connection'
3
+ require 'infusionsoft/request'
4
+
5
+ module Infusionsoft
6
+
7
+ class Api
8
+ include Connection
9
+ include Request
10
+
11
+ attr_accessor *Configuration::VALID_OPTION_KEYS
12
+
13
+ def initialize(options={})
14
+ options = Infusionsoft.options.merge(options)
15
+ Configuration::VALID_OPTION_KEYS.each do |key|
16
+ send("#{key}=", options[key])
17
+ end
18
+ end
19
+
20
+ end
21
+
22
+ end
@@ -0,0 +1,25 @@
1
+ module Infusionsoft
2
+ # Wrapper for the Infusionsoft API
3
+ #
4
+ # @note all services have been separated into different modules
5
+ class Client < Api
6
+ # Require client method modules after initializing the Client class in
7
+ # order to avoid a superclass mismatch error, allowing those modules to be
8
+ # Client-namespaced.
9
+ require 'infusionsoft/client/contact'
10
+ require 'infusionsoft/client/email'
11
+ require 'infusionsoft/client/invoice'
12
+ require 'infusionsoft/client/data'
13
+ require 'infusionsoft/client/affiliate'
14
+ require 'infusionsoft/client/file'
15
+ require 'infusionsoft/client/ticket'
16
+
17
+ include Infusionsoft::Client::Contact
18
+ include Infusionsoft::Client::Email
19
+ include Infusionsoft::Client::Invoice
20
+ include Infusionsoft::Client::Data
21
+ include Infusionsoft::Client::Affiliate
22
+ include Infusionsoft::Client::File
23
+ include Infusionsoft::Client::Ticket
24
+ end
25
+ end
@@ -0,0 +1,52 @@
1
+ module Infusionsoft
2
+ class Client
3
+ ########################
4
+ ### Affiliate Service ##
5
+ ########################
6
+ module Affiliate
7
+ # return all claw backs in a date range
8
+ #
9
+ # @affiliate_id [Integer]
10
+ # @start_date [Date]
11
+ # @end_date [Date]
12
+ def affiliate_clawbacks(affiliate_id, start_date, end_date)
13
+ response = get('APIAffiliateService', 'affClawbacks', affiliate_id, start_date, end_date)
14
+ end
15
+
16
+ # return all commissions in a date range
17
+ #
18
+ # @affiliate_id [Integer]
19
+ # @start_date [Date]
20
+ # @end_date [Date]
21
+ def affiliate_commissions(affiliate_id, start_date, end_date)
22
+ response = get('APIAffiliateService', 'affCommissions', affiliate_id, start_date, end_date)
23
+ end
24
+
25
+ # return all payouts in a date range
26
+ #
27
+ # @affiliate_id [Integer]
28
+ # @start_date [Date]
29
+ # @end_date [Date]
30
+ def affiliate_payouts(affiliate_id, start_date, end_date)
31
+ response = get('APIAffiliateService', 'affPayouts', affiliate_id, start_date, end_date)
32
+ end
33
+
34
+ # returns a list with each row representing a single affiliates totals represented by a map with key
35
+ # one of the names above, and value being the total for the variable
36
+ #
37
+ # @affiliate_list [Array]
38
+ def affiliate_running_totals(affiliate_list)
39
+ response = get('APIAffiliateService', 'affRunningTotals', affiliate_list)
40
+ end
41
+
42
+ # return how much the specified affiliates are owed
43
+ #
44
+ # @affiliate_list [Array]
45
+ # @start_date [Date]
46
+ # @end_date [Date]
47
+ def affiliate_summary(affiliate_list, start_date, end_date)
48
+ response = get('APIAffiliateService', 'affSummary', affiliate_list, start_date, end_date)
49
+ end
50
+ end
51
+ end
52
+ end
@@ -0,0 +1,143 @@
1
+ module Infusionsoft
2
+ class Client
3
+ ########################
4
+ ### Contact Service ###
5
+ ########################
6
+ module Contact
7
+ # Finds all contacts with the supplied email address in any of the three contact record email addresses
8
+ #
9
+ # @email [String]
10
+ # @selected_fields [Array]
11
+ def contact_find_by_email(email, selected_fields)
12
+ response = get('ContactService.findByEmail', email, selected_fields)
13
+ end
14
+
15
+ # Adds a contact to the database, then opts in the email address
16
+ #
17
+ # @data = [Hash]
18
+ # @example data = {:EmailAddress1 => 'test@test.com', :FirstName => 'first_name', :LastName => 'last_name'}
19
+ # @returns [Integer] This is the id of the newly added contact
20
+ def contact_add(data)
21
+ contact_id = get('ContactService.add', data)
22
+ if data.has_key?("Email"); api_email_optin(data["Email"], "requested information"); end
23
+ return contact_id
24
+ end
25
+
26
+ # Creates a new recurring order for a contact.
27
+ #
28
+ # @contact_id [Integer]
29
+ # @allow_duplicate [Boolean]
30
+ # @cprogram_id [Integer]
31
+ # @merchante_account_id [Integer]
32
+ # @credit_card_id [Integer]
33
+ # @affiliate_id [Integer]
34
+ def contact_add_recurring_order(contact_id, allow_duplicate, cprogram_id, merchant_account_id, credit_card_id, affiliate_id,
35
+ days_till_charge)
36
+ response = get('ContactService','addRecurringOrder', contact_id, allow_duplicate, cprogram_id,
37
+ merchant_account_id, credit_card_id, affiliate_id, days_till_charge)
38
+ end
39
+
40
+ # Adds a contact to a group
41
+ #
42
+ # @contact_id [Integer]
43
+ # @group_id [Integer]
44
+ def contact_add_to_group(contact_id, group_id)
45
+ response = get('ContactService', 'addToGroup', contact_id, group_id)
46
+ end
47
+
48
+ def contact_link_contact(remoteApp, remoteId, localId)
49
+ response = get('ContactService', 'linkContact', remoteApp, remoteId, localId)
50
+ end
51
+
52
+ # Loads a contact from the database
53
+ #
54
+ # @id [Integer]
55
+ # @selected_fields [Array]
56
+ def contact_load(id, selected_fields)
57
+ response = get('ContactService', 'load', id, selected_fields)
58
+ end
59
+
60
+ def contact_locate_contact_link(locate_map_id)
61
+ response = get('ContactService', 'locateContactLink', locate_map_id)
62
+ end
63
+
64
+ def contact_mark_link_updated(locate_map_id)
65
+ response = get('ContactService', 'markLinkUpdated', locate_map_id)
66
+ end
67
+
68
+ # Adds a contact to a campaign.
69
+ #
70
+ # @contact_id [Integer]
71
+ # @campaign_id [Integer]
72
+ def contact_add_to_campaign(contact_id, campaign_id)
73
+ response = get('ContactService','addToCampaign', contact_id, campaign_id)
74
+ end
75
+
76
+ # Pauses a campaign for a given contact.
77
+ #
78
+ # @contact_id [Integer]
79
+ # @campaign_id [Integer]
80
+ def contact_pause_campaign(contact_id, campaign_id)
81
+ response = get('ContactService', 'pauseCampaign', contact_id, campaign_id)
82
+ end
83
+
84
+ # Removes a contact from a given campaign.
85
+ #
86
+ # @contact_id [Integer]
87
+ # @campaign_id [Integer]
88
+ def contact_remove_from_campaign(contact_id, campaign_id)
89
+ response = get('ContactService', 'removeFromCampaign', contact_id, campaign_id)
90
+ end
91
+
92
+ # returns the next step in a campaign
93
+ #
94
+ # @contact_id [Integer]
95
+ # @campaign_id [Integer]
96
+ def contact_get_next_campaign_step(contact_id, campaign_id)
97
+ response = get('ContactService', 'getNextCampaignStep', contact_id, campaign_id)
98
+ end
99
+
100
+ # Reschedules a campaign step for a list of contacts
101
+ #
102
+ # @list_of_contacts [Array]
103
+ # @campaign_id [Integer]
104
+ def contact_reschedule_campaign_step(list_of_contacts, campaign_id)
105
+ response = get('ContactService', 'reschedulteCampaignStep', list_of_contacts, campaign_id)
106
+ end
107
+
108
+ # Removes a contact from a given group.
109
+ #
110
+ # @contact_id [Integer]
111
+ # @group_id [Integer]
112
+ def contact_remove_from_group(contact_id, group_id)
113
+ response = get('ContactService', 'removeFromGroup', contact_id, group_id)
114
+ end
115
+
116
+ # Executes an action sequence for a given contact
117
+ def contact_run_action_set(contact_id, action_set_id)
118
+ response = get('ContactService', 'runActionSequence', contact_id, action_set_id)
119
+ end
120
+
121
+ # Executes an action sequence for a given contact, passing in
122
+ # runtime params for running affiliate signup actions, etc
123
+ #
124
+ # @contact_id [Integer]
125
+ # @action_set_id [Integer]
126
+ # @params [Hash]
127
+ def contact_run_action_set_with_params(contact_id, action_set_id, params)
128
+ response = get('ContactService', 'runActionSequence', contact_id, action_set_id, params)
129
+ end
130
+
131
+ # Updates a contact in the database.
132
+ #
133
+ # @contact_id [Integer]
134
+ # @data [Hash]
135
+ # @example {:FirstName => 'first_name', :StreetAddress1 => '123 N Street'}
136
+ def contact_update(contact_id, data)
137
+ bool = get('ContactService', 'update', contact_id, data)
138
+ if data.has_key?("Email"); api_email_optin(data["Email"], "requested information"); end
139
+ return bool
140
+ end
141
+ end
142
+ end
143
+ end
@@ -0,0 +1,90 @@
1
+ module Infusionsoft
2
+ class Client
3
+ ########################
4
+ ### Data Service ###
5
+ ########################
6
+ module Data
7
+ # Adds a record to the database. If you attempt to set fields that are marked read-only
8
+ # by the Data Spec, this operation will simply ignore those fields - not throw an error
9
+ #
10
+ # @table [String]
11
+ # @values [Hash]
12
+ def data_add(table, values)
13
+ response = get('DataService.add', table, values)
14
+ end
15
+
16
+ # This will locate all records in a given table that match the criteria for a given field.
17
+ #
18
+ # @table [String]
19
+ # @limit [Integer]
20
+ # @page [Integer]
21
+ # @field_name [String]
22
+ # @field_value [String]
23
+ # @selected_fields [Array]
24
+ def data_find_by_field(table, limit, page, field_name, field_value, selected_fields)
25
+ response = get('DataService.findByField', table, limit, page, field_name,
26
+ field_value, selected_fields)
27
+ end
28
+
29
+ # This method will load a record from the database given the primary key
30
+ #
31
+ # @table [String]
32
+ # @id [Integer]
33
+ # @selected_fields [Array]
34
+ def data_load(table, id, selected_fields)
35
+ response = get('DataService.load', table, id, selected_fields)
36
+ end
37
+
38
+ # Queries records in a given table to find matches on certain fields
39
+ #
40
+ # @table [String]
41
+ # @limit [Integer]
42
+ # @page [Integer]
43
+ # @data [Hash] The data you would like to query on. { :FirstName => 'first_name' }
44
+ # @selected_fields [Array]
45
+ def data_query(table, limit, page, data, selected_fields)
46
+ response = get('DataService.query', table, limit, page, data, selected_fields)
47
+ end
48
+
49
+ # Updates a given record to the database
50
+ #
51
+ # @table [String]
52
+ # @id [Integer]
53
+ # @values [Hash] This is the fields and values you would like to update
54
+ # @example { :FirstName => 'first_name', :EmailAddress1 => 'test@test.com' }
55
+ def data_update(table, id, values)
56
+ response = get('DataService.update', table, id, values)
57
+ end
58
+
59
+ # Adds a custom field to Infusionsoft
60
+ #
61
+ # @context [String]
62
+ # @label [String]
63
+ # @data_type [String]
64
+ # @group_id [Integer]
65
+ def data_add_custom_field(context, label, data_type, group_id)
66
+ response = get('DataService.addCustomField', context, label, data_type, group_id)
67
+ end
68
+
69
+ # Updates a custom field
70
+ #
71
+ # @field_id [Integer]
72
+ # @field_value
73
+ def data_update_custom_field(field_id, field_value)
74
+ response = get('DataService.updateCustomField', field_id, field_value)
75
+ end
76
+
77
+ # Authenticates a user account in Infusionsoft
78
+ #
79
+ # @username [String]
80
+ # @password [String]
81
+ def data_authenticate_user(username, password)
82
+ response = get('DataService.authenticateUser', username, password)
83
+ end
84
+
85
+ def data_echo(text)
86
+ response = get('DataService.echo', text)
87
+ end
88
+ end
89
+ end
90
+ end
@@ -0,0 +1,91 @@
1
+ module Infusionsoft
2
+ class Client
3
+ ########################
4
+ ### Email Service ###
5
+ ########################
6
+ module Email
7
+ # Enables you to opt contacts in
8
+ #
9
+ # @email [String]
10
+ # @reason [String]
11
+ def email_optin(email, reason)
12
+ response = get('APIEmailService', 'optIn', email, reason)
13
+ end
14
+
15
+ # Enables you to opt contacts out
16
+ #
17
+ # @email [String]
18
+ # @reason [String]
19
+ def email_optout(email, reason)
20
+ response = get('APIEmailService', 'optOut', email, reason)
21
+ end
22
+
23
+ # Sends an email through infusion
24
+ #
25
+ # @contact_list [Array] List of contact ids you want to send this email to
26
+ # @from_address [String]
27
+ # @to_address [String]
28
+ # @cc_address [String]
29
+ # @bcc_address [String]
30
+ # @content_type [String] this must be one of the following Text, HTML, or Multipart
31
+ # @subject [String]
32
+ # @html_body [Text]
33
+ # @text_body [Text]
34
+ def email_send(contact_list, from_address, to_address, cc_addresses, bcc_addresses, content_type, subject, html_body, text_body)
35
+ response = get('APIEmailService', 'sendEmail', contact_list, from_address, to_address, cc_addresses, bcc_addresses, content_type, subject, html_body, text_body)
36
+ end
37
+
38
+ # adds an email template for future use
39
+ #
40
+ # @title [String]
41
+ # @categories [String] a comma separated list of the categories you wan this template in Infusionsoft
42
+ # @content_type [String] can be Text, HTML, Multipart
43
+ # @text_body [Text]
44
+ # @html_body [Text]
45
+ # @merge_context [String] can be Contact, ServiceCall, Opportunity, CreditCard
46
+ def email_add(title, categories, from, to, cc, bcc, subject, text_body, html_body, content_type, merge_context)
47
+ response = get('APIEmailService', 'addEmailTemplate', title, categories, from, to, cc, bcc, subject, text_body, html_body, content_type, merge_context)
48
+ end
49
+
50
+ # Attaches an email to a contact record
51
+ def email_attach(contact_id, from_name, from_address, to_address, cc_addresses, bcc_addresses, content_type, subject, html_body, txt_body, header, receive_date, send_date)
52
+ response = get('APIEmailService', 'attachEmail', contact_id, from_name, from_address, to_address, cc_addresses, bcc_addresses, content_type, subject, html_body, txt_body, header, receive_date, send_date)
53
+ end
54
+
55
+ # Creates an email template
56
+ def email_create_template(title, user_id, from_address, to_addres, cc_addresses, bcc_addresses, content_type, subject, html_body, txt_body)
57
+ response = get('APIEmailService', 'createEmailTemplate', title, user_id, from_address, to_addres, cc_addresses, bcc_addresses, content_type, subject, html_body, txt_body)
58
+ end
59
+
60
+ # updates an email template for future use
61
+ #
62
+ # @categories [String] a comma separated list of the categories you wan this template in Infusionsoft
63
+ # @content_type [String] can be Text, HTML, Multipart
64
+ # @merge_context [String] can be Contact, ServiceCall, Opportunity, CreditCard
65
+ def email_update_template(id, title, categories, from, to, cc, bcc, subject, text_body, html_body, content_type, merge_context)
66
+ response = get('APIEmailService', 'updateEmailTemplate', title, categories, from, to, cc, bcc, subject, text_body, html_body, content_type)
67
+ end
68
+
69
+ # returns an email template
70
+ def email_get_template(id)
71
+ response = get('APIEmailService', 'getEmailTemplate', id)
72
+ end
73
+
74
+ # gets the opt-in status of the provided email address
75
+ #
76
+ # email_address [String]
77
+ # @returns 0 = opted out; 1 = single opt-in; 2 = double opt-in
78
+ def email_get_opt_status(email_address)
79
+ response = get('APIEmailService', 'getOptStatus', email_address)
80
+ end
81
+
82
+ # returns a string of merge fields for a given context
83
+ #
84
+ # @merge_context [String] could include Contact, ServiceCall, Opportunity, CreditCard
85
+ def email_get_available_merge_fields(merge_context)
86
+ response = get('APIEmailService', 'getAvailableMergeFields', merge_context)
87
+ end
88
+
89
+ end
90
+ end
91
+ end
@@ -0,0 +1,29 @@
1
+ module Infusionsoft
2
+ class Client
3
+ ########################
4
+ ### File Service ###
5
+ ########################
6
+ module File
7
+ def file_upload(contact_id, file_name, encoded_file_base64)
8
+ response = get('FileService', 'uploadFile', contact_id, file_name, encoded_file_base64)
9
+ end
10
+
11
+ # returns the Base64 encoded file contents
12
+ def file_get(id)
13
+ response = get('FileService', 'getFile', id)
14
+ end
15
+
16
+ def file_url(id)
17
+ response = get('FileService', 'getDownloadUrl', id)
18
+ end
19
+
20
+ def file_rename(id, new_name)
21
+ response = get('FileService', 'renameFile', id, new_name)
22
+ end
23
+
24
+ def file_replace(id, encoded_file_base64)
25
+ response = get('FileService', 'replaceFile', id, encoded_file_base64)
26
+ end
27
+ end
28
+ end
29
+ end
@@ -0,0 +1,128 @@
1
+ module Infusionsoft
2
+ class Client
3
+ ########################
4
+ ### Invoice Service ###
5
+ ########################
6
+ module Invoice
7
+ def invoice_update_recurring_next_bill_date(job_recurring_id, new_bill_date)
8
+ response = get('InvoiceService', 'updateJobRecurringNextBillDate', job_recurring_id, new_bill_date)
9
+ end
10
+
11
+ # Adds a payment to an invoice without actually processing a charge through a merchant.
12
+ #
13
+ # @invoice_id [Integer]
14
+ # @amount [Float]
15
+ # @date [Date]
16
+ # @type [String] Cash, Check, Credit Card, Money Order, PayPal, etc.
17
+ # @description [String]
18
+ # @bypass_commissions [Boolean]
19
+ # @return [Boolean]
20
+ def invoice_add_manual_payment(invoice_id, amount, date, type, description, bypass_commissions)
21
+ response = get('InvoiceService', 'addManualPayment', invoice_id, amount, date, type,
22
+ description, bypass_commissions)
23
+ end
24
+
25
+ # Adds a commission override to a one time order, using a combination of percentage and hard-coded amounts.
26
+ def invoice_add_order_commission_override(invoice_id, affiliate_id, product_id, percentage, amount, payout_type,
27
+ description, date)
28
+ response = get('InvoiceService', 'addOrderCommissionOverride', invoice_id, affiliate_id, product_id,
29
+ percentage, amount, payout_type, description, date)
30
+ end
31
+
32
+ # Adds an item to an existing order.
33
+ #
34
+ # @order_id [Integer] This is the invoice id
35
+ # @product_id [Integer]
36
+ # @type [Integer] UNKNOWN = 0, SHIPPING = 1, TAX = 2, SERVICE = 3, PRODUCT = 4, UPSELL = 5, FINANCECHARGE = 6, SPECIAL = 7
37
+ # @price [Float]
38
+ # @quantity [Integer]
39
+ # @description [String]
40
+ # @notes [String]
41
+ # @return [Boolean] returns true or false if it was added successfully or not
42
+ def invoice_add_order_item(order_id, product_id, type, price, quantity, description, notes)
43
+ response = get('InvoiceService', 'addOrderItem', order_id, product_id, type, price,
44
+ quantity, description, notes)
45
+ end
46
+
47
+ # Adds a payment plan to an existing invoice.
48
+ def invoice_add_payment_plan(order_id, auto_charge, credit_card_id, merchant_account_id, days_between_retry, max_retry,
49
+ initial_payment_amount, plan_start_date, number_of_payments, days_between_payments)
50
+ response = get('InvoiceService', 'addPaymentPlan', order_id, auto_charge, credit_card_id, merchant_account_id,
51
+ days_between_retry, max_retry, initial_payment_amount, plan_start_date, number_of_payments,
52
+ days_between_payments)
53
+ end
54
+
55
+ # Adds a commission override to a recurring order.
56
+ def invoice_add_recurring_commission_override(recurringorder_id, affiliate_id, amount, payout_type, description)
57
+ response = get('InvoiceService', 'addRecurringCommissionOverride', recurringorder_id, affiliate_id, amount,
58
+ payout_type, description)
59
+ end
60
+
61
+ # Adds a recurring order to the database.
62
+ def invoice_add_recurring_order(contact_id, allow_duplicate, cprogram_id, merchant_account_id, credit_card_id, affiliate_id,
63
+ days_till_charge)
64
+ response = get('InvoiceService', 'addRecurringOrder', contact_id, allow_duplicate, cprogram_id,
65
+ merchant_account_id, credit_card_id, affiliate_id, days_till_charge)
66
+ end
67
+
68
+ # Adds a recurring order to the database.
69
+ def invoice_add_recurring_order_with_price(contact_id, allow_duplicate, cprogram_id, qty, price, allow_tax, merchant_account_id, credit_card_id, affiliate_id, days_till_charge)
70
+ response = get('InvoiceService', 'addRecurringOrder', contact_id, allow_duplicate, cprogram_id, qty, price, allow_tax, merchant_account_id, credit_card_id, affiliate_id, days_till_charge)
71
+ end
72
+
73
+ # Calculates the amount owed for a given invoice.
74
+ def invoice_calculate_amount_owed(invoice_id)
75
+ response = get('InvoiceService', 'calculateAmountOwed', invoice_id)
76
+ end
77
+
78
+ # Will charge an invoice with the amount currently due on it.
79
+ #
80
+ # @invoice_id [Integer]
81
+ # @notes [String]
82
+ # @credit_card_id [Integer]
83
+ # @merchant_account_id [Integer]
84
+ # @bypass_commission [Boolean]
85
+ # @return [Hash] containing the following keys
86
+ # {'Successful => [Boolean], 'Code' => [String], 'RefNum' => [String], 'Message' => [String]}
87
+ def invoice_charge_invoice(invoice_id, notes, credit_card_id, merchant_account_id, bypass_commissions)
88
+ response = get('InvoiceService', 'chargeInvoice', invoice_id, notes, credit_card_id,
89
+ merchant_account_id, bypass_commissions)
90
+ end
91
+
92
+ # returns the invoice id from a one time order
93
+ def invoice_get_invoice_id(order_id)
94
+ response = get('InvoiceService', 'getinvoice_id', order_id)
95
+ end
96
+
97
+ # Creates a blank order with no items.
98
+ #
99
+ # @return [Integer] returns the invoice id
100
+ def invoice_create_blank_order(contact_id, description, order_date, lead_affiliate_id, sale_affiliate_id)
101
+ response = get('InvoiceService', 'createBlankOrder', contact_id, description, order_date,
102
+ lead_affiliate_id, sale_affiliate_id)
103
+ end
104
+
105
+ # This will create an invoice for all charges due on a recurring order.
106
+ def invoice_create_invoice_for_recurring(recurringorder_id)
107
+ response = get('InvoiceService', 'createInvoiceForRecurring', recurringorder_id)
108
+ end
109
+
110
+ # Locates an existing card in the system for a contact, using the
111
+ def invoice_locate_existing_card(contact_id, last4)
112
+ # last 4 digits of the card.
113
+ response = get('InvoiceService', 'locateExistingCard', contact_id, last4)
114
+ end
115
+
116
+ # This will validate a credit card in the system.
117
+ def invoice_validate_card(credit_card_id)
118
+ response = get('InvoiceService', 'validateCreditCard', credit_card_id)
119
+ end
120
+
121
+ # This will validate a credit card by passing in values of the
122
+ # card directly (this card doesn't have to be added to the system)
123
+ def invoice_validate_card(creditCard)
124
+ response = get('InvoiceService', 'validateCreditCard', creditCard)
125
+ end
126
+ end
127
+ end
128
+ end
@@ -0,0 +1,18 @@
1
+ module Infusionsoft
2
+ class Client
3
+ ########################
4
+ ### Ticket Service ###
5
+ ########################
6
+ module Ticket
7
+ # add move notes to existing tickets
8
+ def ticket_add_move_notes(ticket_list, move_notes, move_to_stage_id, notify_ids)
9
+ response = get('ServiceCallService', 'addMoveNotes', ticket_list, move_notes, move_to_stage_id, notify_ids)
10
+ end
11
+
12
+ # add move notes to existing tickets
13
+ def ticket_move_stage(ticket_id, ticket_stage, move_notes, notify_ids)
14
+ response = get('ServiceCallService', 'moveTicketStage', ticket_id, ticket_stage, move_notes, notify_ids)
15
+ end
16
+ end
17
+ end
18
+ end
@@ -0,0 +1,5 @@
1
+ module Infusionsoft
2
+ # The version of the gem
3
+ VERSION = '1.0.0'.freeze unless defined?(::Infusionsoft::VERSION)
4
+ end
5
+
@@ -0,0 +1,36 @@
1
+ module Infusionsoft
2
+
3
+ module Configuration
4
+ VALID_OPTION_KEYS = [
5
+ :api_url,
6
+ :api_key
7
+ ].freeze
8
+
9
+ # @private
10
+ attr_accessor *VALID_OPTION_KEYS
11
+
12
+ # When this module is extended, set all configuration options to their default values
13
+ #def self.extended(base)
14
+ #base.reset
15
+ #end
16
+
17
+ # Convenience method to allow configuration options to be set in a block
18
+ def configure
19
+ yield self
20
+ end
21
+
22
+ # Create a hash of options and their values
23
+ def options
24
+ options = {}
25
+ VALID_OPTION_KEYS.each{|k| options[k] = send(k)}
26
+ options
27
+ end
28
+
29
+ #def reset
30
+ #self.url = ''
31
+ #self.api_key = 'na'
32
+ #end
33
+
34
+ end
35
+
36
+ end
@@ -0,0 +1,48 @@
1
+ require "xmlrpc/client"
2
+
3
+ module Infusionsoft
4
+ module Connection
5
+ private
6
+
7
+ def connection(service_call, *args)
8
+ server = XMLRPC::Client.new3({
9
+ 'host' => api_url,
10
+ 'path' => "/api/xmlrpc",
11
+ 'port' => 443,
12
+ 'use_ssl' => true
13
+ })
14
+ begin
15
+ result = server.call("#{service_call}", api_key, *args)
16
+ rescue XMLRPC::FaultException => e
17
+ puts "*** INFUSION API ERROR: #{e.faultCode} - #{e.faultString} ***"
18
+ end
19
+ return result
20
+ end
21
+
22
+ #end
23
+ #if result.nil?; raise RetryException.new(true, @retry_count), "transient read error" end
24
+ #rescue RetryException => detail
25
+ ## Catch for transietn Infusionsoft connection errors
26
+ #puts "*** INFUSION API ERROR: Transient read error *** retrying: #{@retry_count}"
27
+ #self.retry_count += 1
28
+ #retry if detail.ok_to_retry
29
+ #rescue XMLRPC::FaultException => e
30
+ #puts "*** INFUSION API ERROR: #{e.faultCode} - #{e.faultString} ***"
31
+ #rescue Timeout::Error
32
+ #detail = RetryException.new(true, @retry_count)
33
+ #puts "*** INFUSION API ERROR: Timeout *** retrying #{@retry_count}"
34
+ #@retry_count += 1
35
+ #retry if detail.ok_to_retry
36
+ #rescue
37
+ #detail = RetryException.new(true, @retry_count)
38
+ ## This is most likely a catch for the infamous Content-Type bug from Infusionsoft.
39
+ ## Their response has an issue where it isn't sending back a Content-Type in the header,
40
+ ## which throws an nill error in the xml-rpc client in Ruby.
41
+ ## see xmlrcp/client.rb:552 and xmlrpc/utils.rb:159 in Ruby Standard Library.
42
+ #puts "*** INFUSION API ERROR: Content Type is nil back from Infusionsoft *** retrying: #{@retry_count}"
43
+ #@retry_count += 1
44
+ #retry if detail.ok_to_retry
45
+ #end
46
+
47
+ end
48
+ end
@@ -0,0 +1,33 @@
1
+ module Infusionsoft
2
+ module Request
3
+ # Perform an GET request
4
+ def get(service_call, *args)
5
+ request(:get, service_call, *args)
6
+ end
7
+
8
+ def post(path, params={}, options={})
9
+ request(:post, path, params, options)
10
+ end
11
+
12
+ # Perform an HTTP PUT request
13
+ def put(path, params={}, options={})
14
+ request(:put, path, params, options)
15
+ end
16
+
17
+ # Perform an HTTP DELETE request
18
+ def delete(path, params={}, options={})
19
+ request(:delete, path, params, options)
20
+ end
21
+
22
+
23
+ private
24
+
25
+ # Perform request
26
+ def request(method, service_call, *args)
27
+ case method.to_sym
28
+ when :get
29
+ response = connection(service_call, *args)
30
+ end
31
+ end
32
+ end
33
+ end
@@ -0,0 +1,4 @@
1
+ module Infusionsoft
2
+ # The version of the gem
3
+ VERSION = '1.0.2'.freeze unless defined?(::Infusionsoft::VERSION)
4
+ end
@@ -0,0 +1,8 @@
1
+ require 'test/unit'
2
+
3
+ class ApiInfusionTest < Test::Unit::TestCase
4
+ # Replace this with your real tests.
5
+ def test_this_plugin
6
+ flunk # will implement later :(
7
+ end
8
+ end
metadata ADDED
@@ -0,0 +1,89 @@
1
+ --- !ruby/object:Gem::Specification
2
+ name: infusionsoft
3
+ version: !ruby/object:Gem::Version
4
+ hash: 19
5
+ prerelease:
6
+ segments:
7
+ - 1
8
+ - 0
9
+ - 2
10
+ version: 1.0.2
11
+ platform: ruby
12
+ authors:
13
+ - Nathan Leavitt
14
+ autorequire:
15
+ bindir: bin
16
+ cert_chain: []
17
+
18
+ date: 2011-09-26 00:00:00 -07:00
19
+ default_executable:
20
+ dependencies: []
21
+
22
+ description: A Ruby wrapper written for the Infusionsoft API
23
+ email:
24
+ - nate@infusedsystems.com
25
+ executables: []
26
+
27
+ extensions: []
28
+
29
+ extra_rdoc_files: []
30
+
31
+ files:
32
+ - .gitignore
33
+ - LICENSE.md
34
+ - README.md
35
+ - infusionsoft.gemspec
36
+ - lib/infusionsoft.rb
37
+ - lib/infusionsoft/api.rb
38
+ - lib/infusionsoft/client.rb
39
+ - lib/infusionsoft/client/affiliate.rb
40
+ - lib/infusionsoft/client/contact.rb
41
+ - lib/infusionsoft/client/data.rb
42
+ - lib/infusionsoft/client/email.rb
43
+ - lib/infusionsoft/client/file.rb
44
+ - lib/infusionsoft/client/invoice.rb
45
+ - lib/infusionsoft/client/ticket.rb
46
+ - lib/infusionsoft/client/version.rb
47
+ - lib/infusionsoft/configuration.rb
48
+ - lib/infusionsoft/connection.rb
49
+ - lib/infusionsoft/request.rb
50
+ - lib/infusionsoft/version.rb
51
+ - test/api_infusion_test.rb
52
+ has_rdoc: true
53
+ homepage: https://github.com/nateleavitt/infusionsoft
54
+ licenses: []
55
+
56
+ post_install_message:
57
+ rdoc_options: []
58
+
59
+ require_paths:
60
+ - lib
61
+ required_ruby_version: !ruby/object:Gem::Requirement
62
+ none: false
63
+ requirements:
64
+ - - ">="
65
+ - !ruby/object:Gem::Version
66
+ hash: 3
67
+ segments:
68
+ - 0
69
+ version: "0"
70
+ required_rubygems_version: !ruby/object:Gem::Requirement
71
+ none: false
72
+ requirements:
73
+ - - ">="
74
+ - !ruby/object:Gem::Version
75
+ hash: 23
76
+ segments:
77
+ - 1
78
+ - 3
79
+ - 6
80
+ version: 1.3.6
81
+ requirements: []
82
+
83
+ rubyforge_project:
84
+ rubygems_version: 1.5.0
85
+ signing_key:
86
+ specification_version: 3
87
+ summary: Ruby wrapper for the Infusionsoft API
88
+ test_files: []
89
+