constantcontact 1.0.2 → 1.1.0
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 +4 -4
- data/README.md +127 -136
- data/constantcontact.gemspec +4 -3
- data/lib/constantcontact.rb +63 -44
- data/lib/constantcontact/api.rb +932 -535
- data/lib/constantcontact/auth/oauth2.rb +86 -66
- data/lib/constantcontact/components/account/verified_email_address.rb +14 -14
- data/lib/constantcontact/components/activities/activity.rb +30 -30
- data/lib/constantcontact/components/activities/activity_error.rb +14 -14
- data/lib/constantcontact/components/activities/add_contacts.rb +1 -1
- data/lib/constantcontact/components/activities/add_contacts_import_data.rb +37 -36
- data/lib/constantcontact/components/component.rb +25 -0
- data/lib/constantcontact/components/contacts/address.rb +12 -12
- data/lib/constantcontact/components/contacts/contact.rb +50 -44
- data/lib/constantcontact/components/contacts/contact_list.rb +12 -12
- data/lib/constantcontact/components/contacts/custom_field.rb +14 -14
- data/lib/constantcontact/components/contacts/email_address.rb +14 -14
- data/lib/constantcontact/components/contacts/note.rb +13 -13
- data/lib/constantcontact/components/email_marketing/campaign.rb +41 -41
- data/lib/constantcontact/components/email_marketing/click_through_details.rb +14 -14
- data/lib/constantcontact/components/email_marketing/message_footer.rb +14 -14
- data/lib/constantcontact/components/email_marketing/schedule.rb +14 -15
- data/lib/constantcontact/components/email_marketing/test_send.rb +21 -21
- data/lib/constantcontact/components/event_spot/contact.rb +27 -0
- data/lib/constantcontact/components/event_spot/event.rb +63 -0
- data/lib/constantcontact/components/event_spot/event_track.rb +28 -0
- data/lib/constantcontact/components/event_spot/fee.rb +27 -0
- data/lib/constantcontact/components/event_spot/guest.rb +31 -0
- data/lib/constantcontact/components/event_spot/notification_option.rb +27 -0
- data/lib/constantcontact/components/event_spot/promo_code.rb +26 -0
- data/lib/constantcontact/components/event_spot/registrant.rb +54 -0
- data/lib/constantcontact/components/event_spot/registrant_field.rb +27 -0
- data/lib/constantcontact/components/event_spot/registrant_section.rb +34 -0
- data/lib/constantcontact/components/event_spot/sale_item.rb +27 -0
- data/lib/constantcontact/components/library/file/library_file.rb +27 -0
- data/lib/constantcontact/components/library/folder/library_folder.rb +26 -0
- data/lib/constantcontact/components/library/info/library_summary.rb +26 -0
- data/lib/constantcontact/components/library/info/move_results.rb +26 -0
- data/lib/constantcontact/components/library/info/upload_status.rb +26 -0
- data/lib/constantcontact/components/tracking/bounce_activity.rb +14 -14
- data/lib/constantcontact/components/tracking/click_activity.rb +14 -14
- data/lib/constantcontact/components/tracking/forward_activity.rb +14 -14
- data/lib/constantcontact/components/tracking/open_activity.rb +14 -14
- data/lib/constantcontact/components/tracking/send_activity.rb +14 -14
- data/lib/constantcontact/components/tracking/tracking_summary.rb +17 -17
- data/lib/constantcontact/components/tracking/unsubscribe_activity.rb +14 -14
- data/lib/constantcontact/services/account_service.rb +4 -3
- data/lib/constantcontact/services/activity_service.rb +40 -3
- data/lib/constantcontact/services/base_service.rb +34 -6
- data/lib/constantcontact/services/campaign_tracking_service.rb +20 -20
- data/lib/constantcontact/services/contact_service.rb +10 -12
- data/lib/constantcontact/services/contact_tracking_service.rb +20 -20
- data/lib/constantcontact/services/email_marketing_service.rb +8 -10
- data/lib/constantcontact/services/event_spot_service.rb +254 -0
- data/lib/constantcontact/services/library_service.rb +297 -0
- data/lib/constantcontact/services/list_service.rb +6 -5
- data/lib/constantcontact/util/config.rb +135 -117
- data/lib/constantcontact/version.rb +1 -1
- data/spec/constantcontact/api_spec.rb +1223 -173
- data/spec/constantcontact/auth/oauth2_spec.rb +60 -47
- data/spec/constantcontact/components/contacts/address_spec.rb +1 -1
- data/spec/constantcontact/components/contacts/contact_list_spec.rb +1 -1
- data/spec/constantcontact/components/contacts/contact_spec.rb +1 -1
- data/spec/constantcontact/components/contacts/email_address_spec.rb +1 -1
- data/spec/constantcontact/services/activity_service_spec.rb +201 -0
- data/spec/constantcontact/services/base_service_spec.rb +27 -0
- data/spec/constantcontact/services/campaign_schedule_service_spec.rb +111 -0
- data/spec/constantcontact/services/campaign_tracking_service_spec.rb +127 -0
- data/spec/constantcontact/services/contact_service_spec.rb +24 -22
- data/spec/constantcontact/services/contact_tracking_service_spec.rb +127 -0
- data/spec/constantcontact/services/email_marketing_spec.rb +72 -66
- data/spec/constantcontact/services/event_spot_spec.rb +217 -0
- data/spec/constantcontact/services/library_service_spec.rb +248 -0
- data/spec/constantcontact/services/list_service_spec.rb +33 -17
- data/spec/spec_helper.rb +3 -1
- metadata +63 -7
@@ -5,81 +5,101 @@
|
|
5
5
|
# Copyright (c) 2013 Constant Contact. All rights reserved.
|
6
6
|
|
7
7
|
module ConstantContact
|
8
|
-
|
9
|
-
|
10
|
-
|
8
|
+
module Auth
|
9
|
+
class OAuth2
|
10
|
+
attr_accessor :client_id, :client_secret, :redirect_uri, :props
|
11
11
|
|
12
12
|
|
13
|
-
|
14
|
-
|
15
|
-
|
16
|
-
|
17
|
-
|
18
|
-
|
19
|
-
|
20
|
-
|
21
|
-
|
22
|
-
|
23
|
-
|
24
|
-
|
25
|
-
|
26
|
-
|
13
|
+
# Class constructor
|
14
|
+
# @param [Hash] opts - the options to create an OAuth2 object with
|
15
|
+
# @option opts [String] :api_key - the Constant Contact API Key
|
16
|
+
# @option opts [String] :api_secret - the Constant Contact secret key
|
17
|
+
# @option opts [String] :redirect_url - the URL where Constact Contact is returning the authorization code
|
18
|
+
# @return
|
19
|
+
def initialize(opts = {})
|
20
|
+
@client_id = opts[:api_key] || Util::Config.get('auth.api_key')
|
21
|
+
@client_secret = opts[:api_secret] || Util::Config.get('auth.api_secret')
|
22
|
+
@redirect_uri = opts[:redirect_url] || Util::Config.get('auth.redirect_uri')
|
23
|
+
if @client_id.nil? || @client_id == '' || @client_secret.nil? || @client_secret.nil? || @redirect_uri.nil? || @redirect_uri == ''
|
24
|
+
raise ArgumentError.new "Either api_key, api_secret or redirect_uri is missing in explicit call or configuration."
|
25
|
+
end
|
26
|
+
end
|
27
27
|
|
28
28
|
|
29
|
-
|
30
|
-
|
31
|
-
|
32
|
-
|
33
|
-
|
34
|
-
|
35
|
-
|
36
|
-
|
37
|
-
|
38
|
-
|
39
|
-
|
40
|
-
|
41
|
-
|
42
|
-
|
43
|
-
|
44
|
-
|
45
|
-
|
29
|
+
# Get the URL at which the user can authenticate and authorize the requesting application
|
30
|
+
# @param [Boolean] server - whether or not to use OAuth2 server flow, alternative is client flow
|
31
|
+
# @param [String] state - an optional value used by the client to maintain state between the request and callback
|
32
|
+
# @return [String] the authorization URL
|
33
|
+
def get_authorization_url(server = true, state = nil)
|
34
|
+
response_type = server ? Util::Config.get('auth.response_type_code') : Util::Config.get('auth.response_type_token')
|
35
|
+
params = {
|
36
|
+
:response_type => response_type,
|
37
|
+
:client_id => @client_id,
|
38
|
+
:redirect_uri => @redirect_uri
|
39
|
+
}
|
40
|
+
if state
|
41
|
+
params[:state] = state
|
42
|
+
end
|
43
|
+
[
|
44
|
+
Util::Config.get('auth.base_url'),
|
45
|
+
Util::Config.get('auth.authorization_endpoint'),
|
46
|
+
'?',
|
47
|
+
Util::Helpers.http_build_query(params)
|
48
|
+
].join
|
49
|
+
end
|
46
50
|
|
47
51
|
|
48
|
-
|
49
|
-
|
50
|
-
|
51
|
-
|
52
|
-
|
53
|
-
|
54
|
-
|
55
|
-
|
56
|
-
|
57
|
-
|
58
|
-
|
52
|
+
# Obtain an access token
|
53
|
+
# @param [String] code - the code returned from Constant Contact after a user has granted access to his account
|
54
|
+
# @return [String] the access token
|
55
|
+
def get_access_token(code)
|
56
|
+
params = {
|
57
|
+
:grant_type => Util::Config.get('auth.authorization_code_grant_type'),
|
58
|
+
:client_id => @client_id,
|
59
|
+
:client_secret => @client_secret,
|
60
|
+
:code => code,
|
61
|
+
:redirect_uri => @redirect_uri
|
62
|
+
}
|
59
63
|
|
60
|
-
|
61
|
-
|
62
|
-
|
63
|
-
|
64
|
+
url = [
|
65
|
+
Util::Config.get('auth.base_url'),
|
66
|
+
Util::Config.get('auth.token_endpoint')
|
67
|
+
].join
|
64
68
|
|
65
|
-
|
66
|
-
|
67
|
-
|
68
|
-
|
69
|
-
|
70
|
-
|
71
|
-
|
72
|
-
|
73
|
-
|
69
|
+
response_body = ''
|
70
|
+
begin
|
71
|
+
response = RestClient.post(url, params)
|
72
|
+
response_body = JSON.parse(response)
|
73
|
+
rescue => e
|
74
|
+
response_body = e.respond_to?(:response) ?
|
75
|
+
JSON.parse(e.response) :
|
76
|
+
{'error' => '', 'error_description' => e.message}
|
77
|
+
end
|
74
78
|
|
75
|
-
|
76
|
-
|
77
|
-
|
78
|
-
|
79
|
+
if response_body['error_description']
|
80
|
+
error = response_body['error_description']
|
81
|
+
raise Exceptions::OAuth2Exception, error
|
82
|
+
end
|
79
83
|
|
80
|
-
|
81
|
-
|
84
|
+
response_body
|
85
|
+
end
|
82
86
|
|
83
|
-
|
84
|
-
|
87
|
+
|
88
|
+
# Get an information about an access token
|
89
|
+
# @param [String] access_token - Constant Contact OAuth2 access token
|
90
|
+
# @return array
|
91
|
+
def get_token_info(access_token)
|
92
|
+
params = {
|
93
|
+
:access_token => access_token
|
94
|
+
}
|
95
|
+
url = [
|
96
|
+
Util::Config.get('auth.base_url'),
|
97
|
+
Util::Config.get('auth.token_info')
|
98
|
+
].join
|
99
|
+
response = RestClient.post(url, params)
|
100
|
+
response_body = JSON.parse(response)
|
101
|
+
end
|
102
|
+
|
103
|
+
end
|
104
|
+
end
|
85
105
|
end
|
@@ -9,18 +9,18 @@ module ConstantContact
|
|
9
9
|
class VerifiedEmailAddress < Component
|
10
10
|
attr_accessor :status, :email_address
|
11
11
|
|
12
|
-
|
13
|
-
|
14
|
-
|
15
|
-
|
16
|
-
|
17
|
-
|
18
|
-
|
19
|
-
|
20
|
-
|
21
|
-
|
22
|
-
|
23
|
-
|
24
|
-
|
25
|
-
|
12
|
+
# Factory method to create a VerifiedEmailAddress object from a json string
|
13
|
+
# @param [Hash] props - properties to create object from
|
14
|
+
# @return [VerifiedEmailAddress]
|
15
|
+
def self.create(props)
|
16
|
+
obj = VerifiedEmailAddress.new
|
17
|
+
if props
|
18
|
+
props.each do |key, value|
|
19
|
+
obj.send("#{key}=", value) if obj.respond_to? key
|
20
|
+
end
|
21
|
+
end
|
22
|
+
obj
|
23
|
+
end
|
24
|
+
end
|
25
|
+
end
|
26
26
|
end
|
@@ -10,34 +10,34 @@ module ConstantContact
|
|
10
10
|
attr_accessor :id, :type, :status, :start_date, :finish_date, :file_name, :created_date,
|
11
11
|
:error_count, :errors, :warnings, :contact_count
|
12
12
|
|
13
|
-
|
14
|
-
|
15
|
-
|
16
|
-
|
17
|
-
|
18
|
-
|
19
|
-
|
20
|
-
|
21
|
-
|
22
|
-
|
23
|
-
|
24
|
-
|
25
|
-
|
26
|
-
|
27
|
-
|
28
|
-
|
29
|
-
|
30
|
-
|
31
|
-
|
32
|
-
|
33
|
-
|
34
|
-
|
35
|
-
|
36
|
-
|
37
|
-
|
38
|
-
|
39
|
-
|
40
|
-
|
41
|
-
|
42
|
-
|
13
|
+
# Factory method to create an Activity object from a json string
|
14
|
+
# @param [Hash] props - properties to create object from
|
15
|
+
# @return [Activity]
|
16
|
+
def self.create(props)
|
17
|
+
obj = Activity.new
|
18
|
+
if props
|
19
|
+
props.each do |key, value|
|
20
|
+
if key == 'errors'
|
21
|
+
if value
|
22
|
+
obj.errors = []
|
23
|
+
value.each do |error|
|
24
|
+
obj.errors << Components::ActivityError.create(error)
|
25
|
+
end
|
26
|
+
end
|
27
|
+
elsif key == 'warnings'
|
28
|
+
if value
|
29
|
+
obj.warnings = []
|
30
|
+
value.each do |error|
|
31
|
+
obj.warnings << Components::ActivityError.create(error)
|
32
|
+
end
|
33
|
+
end
|
34
|
+
else
|
35
|
+
obj.send("#{key}=", value) if obj.respond_to? key
|
36
|
+
end
|
37
|
+
end
|
38
|
+
end
|
39
|
+
obj
|
40
|
+
end
|
41
|
+
end
|
42
|
+
end
|
43
43
|
end
|
@@ -9,18 +9,18 @@ module ConstantContact
|
|
9
9
|
class ActivityError < Component
|
10
10
|
attr_accessor :message, :line_number, :email_address
|
11
11
|
|
12
|
-
|
13
|
-
|
14
|
-
|
15
|
-
|
16
|
-
|
17
|
-
|
18
|
-
|
19
|
-
|
20
|
-
|
21
|
-
|
22
|
-
|
23
|
-
|
24
|
-
|
25
|
-
|
12
|
+
# Factory method to create an ActivityError object from an array
|
13
|
+
# @param [Hash] props - hash of properties to create object from
|
14
|
+
# @return [ActivityError]
|
15
|
+
def self.create(props)
|
16
|
+
obj = ActivityError.new
|
17
|
+
if props
|
18
|
+
props.each do |key, value|
|
19
|
+
obj.send("#{key}=", value) if obj.respond_to? key
|
20
|
+
end
|
21
|
+
end
|
22
|
+
obj
|
23
|
+
end
|
24
|
+
end
|
25
|
+
end
|
26
26
|
end
|
@@ -102,7 +102,7 @@ module ConstantContact
|
|
102
102
|
if !contact.custom_fields.nil?
|
103
103
|
contact.custom_fields.each do |custom_field|
|
104
104
|
if custom_field.name.match('custom_field_')
|
105
|
-
custom_field_number = custom_field.name[13, custom_field.length]
|
105
|
+
custom_field_number = custom_field.name[13, custom_field.name.length]
|
106
106
|
used_columns << Util::Config.get('activities_columns.custom_field_' + custom_field_number)
|
107
107
|
end
|
108
108
|
end
|
@@ -5,40 +5,41 @@
|
|
5
5
|
# Copyright (c) 2013 Constant Contact. All rights reserved.
|
6
6
|
|
7
7
|
module ConstantContact
|
8
|
-
|
9
|
-
|
10
|
-
|
11
|
-
|
12
|
-
|
13
|
-
|
14
|
-
|
15
|
-
|
16
|
-
|
17
|
-
|
18
|
-
|
19
|
-
|
20
|
-
|
21
|
-
|
22
|
-
|
23
|
-
|
24
|
-
|
25
|
-
|
26
|
-
|
27
|
-
|
28
|
-
|
29
|
-
|
30
|
-
|
31
|
-
|
32
|
-
|
33
|
-
|
34
|
-
|
35
|
-
|
36
|
-
|
37
|
-
|
38
|
-
|
39
|
-
|
40
|
-
|
41
|
-
|
42
|
-
|
43
|
-
|
8
|
+
module Components
|
9
|
+
class AddContactsImportData < Component
|
10
|
+
attr_accessor :first_name, :middle_name, :last_name, :job_title, :company_name,
|
11
|
+
:work_phone, :home_phone, :email_addresses, :addresses, :custom_fields
|
12
|
+
|
13
|
+
|
14
|
+
# Constructor to create an AddContactsImportData object from the given hash
|
15
|
+
# @param [Hash] props - properties to create object from
|
16
|
+
# @return [AddContactsImportData]
|
17
|
+
def initialize(props = {})
|
18
|
+
instance_variables.each do |property, value|
|
19
|
+
send("#{property}=", get_value(props, property)) if obj.respond_to? property
|
20
|
+
end
|
21
|
+
end
|
22
|
+
|
23
|
+
# Setter
|
24
|
+
def add_custom_field(custom_field)
|
25
|
+
@custom_fields = [] if @custom_fields.nil?
|
26
|
+
@custom_fields << custom_field
|
27
|
+
end
|
28
|
+
|
29
|
+
|
30
|
+
# Setter
|
31
|
+
def add_address(address)
|
32
|
+
@addresses = [] if @addresses.nil?
|
33
|
+
@addresses << address
|
34
|
+
end
|
35
|
+
|
36
|
+
|
37
|
+
# Setter
|
38
|
+
def add_email(email_address)
|
39
|
+
@email_addresses = [] if @email_addresses.nil?
|
40
|
+
@email_addresses << email_address
|
41
|
+
end
|
42
|
+
|
43
|
+
end
|
44
|
+
end
|
44
45
|
end
|
@@ -7,6 +7,31 @@
|
|
7
7
|
module ConstantContact
|
8
8
|
module Components
|
9
9
|
class Component
|
10
|
+
|
11
|
+
def to_hash
|
12
|
+
hash = Hash.new
|
13
|
+
self.instance_variables.collect do |var|
|
14
|
+
hash[var.to_s[1..-1]] = self.class.to_hash_value(self.instance_variable_get(var))
|
15
|
+
end
|
16
|
+
hash
|
17
|
+
end
|
18
|
+
|
19
|
+
def self.to_hash_value(val)
|
20
|
+
if val.is_a? ConstantContact::Components::Component
|
21
|
+
return val.to_hash
|
22
|
+
elsif val.is_a? Array
|
23
|
+
return val.collect{|subval| Component.to_hash_value(subval) }
|
24
|
+
elsif val.is_a? DateTime
|
25
|
+
return val.to_s
|
26
|
+
else
|
27
|
+
return val
|
28
|
+
end
|
29
|
+
end
|
30
|
+
|
31
|
+
def to_json(val = nil)
|
32
|
+
self.to_hash.to_json
|
33
|
+
end
|
34
|
+
|
10
35
|
protected
|
11
36
|
|
12
37
|
# Get the requested value from a hash, or return the default
|
@@ -10,18 +10,18 @@ module ConstantContact
|
|
10
10
|
attr_accessor :id, :line1, :line2, :line3, :city, :address_type, :state_code,
|
11
11
|
:country_code, :postal_code, :sub_postal_code
|
12
12
|
|
13
|
-
|
14
|
-
|
15
|
-
|
16
|
-
|
17
|
-
|
18
|
-
|
19
|
-
|
20
|
-
|
21
|
-
|
22
|
-
|
23
|
-
|
24
|
-
|
13
|
+
# Factory method to create an Address object from a json string
|
14
|
+
# @param [Hash] props - properties to create object from
|
15
|
+
# @return [Address]
|
16
|
+
def self.create(props)
|
17
|
+
obj = Address.new
|
18
|
+
if props
|
19
|
+
props.each do |key, value|
|
20
|
+
obj.send("#{key}=", value) if obj.respond_to? key
|
21
|
+
end
|
22
|
+
end
|
23
|
+
obj
|
24
|
+
end
|
25
25
|
end
|
26
26
|
end
|
27
27
|
end
|