gogogibbon 2.0.0

Sign up to get free protection for your applications and to get access to all the features.
checksums.yaml ADDED
@@ -0,0 +1,7 @@
1
+ ---
2
+ SHA256:
3
+ metadata.gz: 67f93827920932b5384a0fd9554480650fcdeed698343cb2c022140992276f9d
4
+ data.tar.gz: 451d17a1a97d08e88fc44dd6c8f69edf9d9a372c322e536a3edf2501b05fe66b
5
+ SHA512:
6
+ metadata.gz: 6be359084aa1139bcc02d071bf68017a50132dfc025e054abda77cca37558c56b401c3a7ee9043c48e257225b7c22134b7de8811aa4c4ea0d60ebe62d7125ba7
7
+ data.tar.gz: f4465841d537ac0b149f4e7bc3dc18e58ec1486b6b31317d69e8d4db67fe1d62af11b649c7eadf1442cd64d15b45bb994645438c481940a7233c802483043981
@@ -0,0 +1,15 @@
1
+ require File.expand_path('../lib/gogogibbon/version', __FILE__)
2
+
3
+ Gem::Specification.new do |s|
4
+ s.name = 'gogogibbon'
5
+ s.version = GoGoGibbon::VERSION
6
+ s.summary = 'Useful helpers for Gibbon'
7
+ s.description = 'A wrapper for Gibbon containing useful helper methods.'
8
+ s.authors = ['GoGoCarl']
9
+ s.email = 'carl.scott@solertium.com'
10
+ s.files = Dir['lib/**/*'] + Dir['*.rb'] + ["gogogibbon.gemspec"]
11
+ s.require_paths = ["lib"]
12
+ s.homepage = 'http://github.com/GoGoCarl/gogogibbon'
13
+
14
+ s.add_dependency 'gibbon', '~> 2.2'
15
+ end
@@ -0,0 +1,42 @@
1
+ module GoGoGibbon
2
+
3
+ class Callbacks
4
+
5
+ def initialize opts={}
6
+ @options = { :thread => false }
7
+ @options.merge! opts
8
+ end
9
+
10
+ def after_create record
11
+ run do
12
+ GoGoGibbon.subscribe record
13
+ end
14
+ end
15
+
16
+ def after_update record
17
+ if record.email_changed? || record.first_name_changed? || record.last_name_changed?
18
+ run do
19
+ GoGoGibbon.update_subscription record.email_was, record
20
+ end
21
+ end
22
+ end
23
+
24
+ def after_destroy record
25
+ run do
26
+ GoGoGibbon.cancel_user record
27
+ end
28
+ end
29
+
30
+ def run &block
31
+ if @options[:thread] == true
32
+ Thread.new do
33
+ yield
34
+ end
35
+ else
36
+ yield
37
+ end
38
+ end
39
+
40
+ end
41
+
42
+ end
@@ -0,0 +1,173 @@
1
+ require 'gibbon'
2
+
3
+ module GoGoGibbon
4
+ module Commands
5
+ class << self
6
+ # Store a hash of list name to ID
7
+ LIST_CACHE = {}
8
+
9
+ #
10
+ # Subscribe to the subscription list
11
+ #
12
+ def subscribe user, list_name=sub_list
13
+ result = false
14
+ sub_id = list list_name
15
+ unless sub_id.nil?
16
+ begin
17
+ body = {
18
+ 'email_address' => user.email,
19
+ 'status' => 'subscribed',
20
+ 'merge_fields' => { 'FNAME' => user.first_name, 'LNAME' => user.last_name }
21
+ }
22
+ result = chimp.lists(sub_id).members.create(body: body)
23
+ rescue Gibbon::MailChimpError => e
24
+ raise e unless e.body['status'] == 400 && e.body['title'] == 'Member Exists'
25
+ end
26
+ end
27
+ result
28
+ end
29
+
30
+ def subscribe_set users, list_name=sub_list
31
+ result = false
32
+
33
+ sub_id = list list_name
34
+ unless sub_id.nil?
35
+ batch = []
36
+
37
+ defaults = { 'method' => 'POST', 'path' => "lists/#{sub_id}/members" }
38
+ handler = lambda do |user|
39
+ batch << defaults.merge("body" => {
40
+ 'email_address' => user.email, 'status' => 'subscribed',
41
+ 'merge_fields' => { 'FNAME' => user.first_name, 'LNAME' => user.last_name }
42
+ }.to_json)
43
+ end
44
+
45
+ if users.respond_to? :find_each
46
+ users.find_each { |user| handler.call(user) }
47
+ else
48
+ users.each { |user| handler.call(user) }
49
+ end
50
+
51
+ body = { "operations" => batch }
52
+
53
+ result = chimp.batches.create(body: body)
54
+ batch_id = result['id']
55
+ attempts = 1, backoff = 2
56
+ while result['status'] != 'finished' && attempts <= 10
57
+ sleep attempts * backoff
58
+ result = chimp.batches(batch_id).retrieve
59
+ attempts += 1
60
+ end
61
+
62
+ if result['status'] == 'finished'
63
+ result = {
64
+ 'add_count' => result['finished_operations'],
65
+ 'update_count' => 0,
66
+ 'error_count' => result['errored_operations'],
67
+ 'total_count' => result['total_operations'],
68
+ 'errors' => []
69
+ }
70
+
71
+ else
72
+ result = false
73
+ end
74
+
75
+ end
76
+ result
77
+ end
78
+
79
+ def unsubscribe user, list_name=unsub_list
80
+ result = false
81
+
82
+ sub_id = list list_name
83
+ unless sub_id.nil?
84
+ begin
85
+ result = chimp.lists(sub_id).members(user_id(user.email)).delete
86
+ rescue Gibbon::MailChimpError => e
87
+ if e.body['status'] == 404
88
+ return true
89
+ else
90
+ raise e
91
+ end
92
+ end
93
+ end
94
+ result.nil?
95
+ end
96
+
97
+ #
98
+ # Unsubscribe from the subscription list,
99
+ # subscribe to the unsubscription list.
100
+ #
101
+ def cancel_user user
102
+ result = false
103
+ unsubscribe user, sub_list
104
+ result = subscribe user, unsub_list
105
+ result
106
+ end
107
+
108
+ def list list_name
109
+ return LIST_CACHE[list_name] if LIST_CACHE.key?(list_name)
110
+ items = lists
111
+ list = nil
112
+ if items
113
+ p = items.select { |i| i['name'] == list_name }
114
+ if p.any?
115
+ list = p.first['id']
116
+ end
117
+ end
118
+ list
119
+ end
120
+
121
+ def update_subscription old_email, user, list_name=sub_list
122
+ result = false
123
+
124
+ sub_id = list list_name
125
+ unless sub_id.nil?
126
+ if old_email != user.email
127
+ unsubscribe Struct.new(:email).new(old_email), list_name
128
+ end
129
+
130
+ body = {
131
+ 'email_address' => user.email, 'status' => 'subscribed',
132
+ 'merge_fields' => { 'FNAME' => user.first_name, 'LNAME' => user.last_name }
133
+ }
134
+
135
+ result = chimp.lists(sub_id).members(user_id(user.email)).upsert(body: body)
136
+ end
137
+ result
138
+ end
139
+
140
+ def lists
141
+ result = nil
142
+ begin
143
+ result = chimp.lists.retrieve(params: { "count" => 100, "fields" => "lists.id,lists.name" })["lists"]
144
+ result.each do |item|
145
+ LIST_CACHE[item['name']] = item['id']
146
+ end
147
+ rescue Gibbon::MailChimpError => e
148
+ puts e.detail
149
+ raise e unless e.body['status'] == 200
150
+ end
151
+ result
152
+ end
153
+
154
+ def chimp
155
+ GoGoGibbon::Config.chimp
156
+ end
157
+
158
+ def sub_list
159
+ GoGoGibbon::Config.subscribed
160
+ end
161
+
162
+ def unsub_list
163
+ GoGoGibbon::Config.unsubscribed
164
+ end
165
+
166
+ private
167
+
168
+ def user_id email
169
+ Digest::MD5.new.update(email.downcase).hexdigest
170
+ end
171
+ end
172
+ end
173
+ end
@@ -0,0 +1,28 @@
1
+ require 'gibbon'
2
+
3
+ module GoGoGibbon
4
+ class Config
5
+ class << self
6
+
7
+ attr_accessor :subscribed, :unsubscribed, :api_key, :chimp, :errors, :on_fail
8
+
9
+ def api_key=(value)
10
+ @chimp = Gibbon::Request.new api_key: value
11
+ @api_key = value
12
+ end
13
+
14
+ def configured?
15
+ !(@api_key.nil? || @subscribed.nil?)
16
+ end
17
+
18
+ def fail!
19
+ msg = 'MailChimp Configuration not complete. Please specify an api_key and subscription list.'
20
+ if @on_fail == :error
21
+ raise Exception.new msg
22
+ else
23
+ puts msg unless @on_fail == :silent
24
+ end
25
+ end
26
+ end
27
+ end
28
+ end
@@ -0,0 +1,48 @@
1
+ module GoGoGibbon
2
+ module Methods
3
+
4
+ def self.included base
5
+ base.send :extend, ClassMethods
6
+ end
7
+
8
+ module ClassMethods
9
+ #
10
+ # Options map can contain the following:
11
+ # * :thread -- true to run in a new thread, false otherwise (default false)
12
+ #
13
+
14
+ #
15
+ # When a user is created, subscribe that user to the mailing list
16
+ #
17
+ def mailchimp_on_create opts={}
18
+ after_create GoGoGibbon::Callbacks.new opts
19
+ end
20
+
21
+ #
22
+ # When a user is updated, update their profile, if necessary
23
+ #
24
+ def mailchimp_on_update opts={}
25
+ after_update GoGoGibbon::Callbacks.new opts
26
+ end
27
+
28
+ #
29
+ # When a user is deleted, cancel that user.
30
+ #
31
+ def mailchimp_on_destroy opts={}
32
+ after_destroy GoGoGibbon::Callbacks.new opts
33
+ end
34
+
35
+ #
36
+ # Return a list of users eligible to receive mail. Defaults to this class,
37
+ # but can return anything relation
38
+ #
39
+ def Mailable
40
+ self
41
+ end
42
+
43
+ end
44
+
45
+ end
46
+ end
47
+
48
+ ActiveRecord::Base.send :include, GoGoGibbon::Methods
@@ -0,0 +1,3 @@
1
+ module GoGoGibbon
2
+ VERSION = '2.0.0'
3
+ end
data/lib/gogogibbon.rb ADDED
@@ -0,0 +1,59 @@
1
+ require 'gogogibbon/commands'
2
+ require 'gogogibbon/config'
3
+ require 'gogogibbon/version'
4
+ require 'gogogibbon/callbacks'
5
+ require 'gogogibbon/methods'
6
+
7
+ module GoGoGibbon
8
+ class << self
9
+
10
+ #
11
+ # Add a new user to the MailChimp subscription list
12
+ #
13
+ def subscribe user
14
+ execute { GoGoGibbon::Commands.subscribe user }
15
+ end
16
+
17
+ #
18
+ # Remove the user from the MailChimp subscription list. If there is
19
+ # a cancellation list configured, they will be subscribed to that.
20
+ #
21
+ def cancel_user user
22
+ execute { GoGoGibbon::Commands.cancel_user user }
23
+ end
24
+
25
+ #
26
+ # Update a user subscription given a user with the properties
27
+ # email, first_name, and last_name. You can always pass a struct
28
+ # with these properties if your user object has these fields named
29
+ # differently.
30
+ #
31
+ def update_subscription old_email, user
32
+ execute { GoGoGibbon::Commands.update_subscription old_email, user }
33
+ end
34
+
35
+ def execute &block
36
+ return unless ready?
37
+ yield
38
+ rescue Exception => e
39
+ if GoGoGibbon::Config.errors = :throw
40
+ raise e
41
+ else
42
+ return false
43
+ end
44
+ end
45
+
46
+ #
47
+ # Returns true if Gibbon has enough information to run, false otherwise.
48
+ # API Key and subscription list are minimally required.
49
+ #
50
+ def ready?
51
+ result = GoGoGibbon::Config.configured?
52
+ unless result
53
+ GoGoGibbon::Config.fail!
54
+ end
55
+ result
56
+ end
57
+
58
+ end
59
+ end
metadata ADDED
@@ -0,0 +1,63 @@
1
+ --- !ruby/object:Gem::Specification
2
+ name: gogogibbon
3
+ version: !ruby/object:Gem::Version
4
+ version: 2.0.0
5
+ platform: ruby
6
+ authors:
7
+ - GoGoCarl
8
+ autorequire:
9
+ bindir: bin
10
+ cert_chain: []
11
+ date: 2020-03-20 00:00:00.000000000 Z
12
+ dependencies:
13
+ - !ruby/object:Gem::Dependency
14
+ name: gibbon
15
+ requirement: !ruby/object:Gem::Requirement
16
+ requirements:
17
+ - - "~>"
18
+ - !ruby/object:Gem::Version
19
+ version: '2.2'
20
+ type: :runtime
21
+ prerelease: false
22
+ version_requirements: !ruby/object:Gem::Requirement
23
+ requirements:
24
+ - - "~>"
25
+ - !ruby/object:Gem::Version
26
+ version: '2.2'
27
+ description: A wrapper for Gibbon containing useful helper methods.
28
+ email: carl.scott@solertium.com
29
+ executables: []
30
+ extensions: []
31
+ extra_rdoc_files: []
32
+ files:
33
+ - gogogibbon.gemspec
34
+ - lib/gogogibbon.rb
35
+ - lib/gogogibbon/callbacks.rb
36
+ - lib/gogogibbon/commands.rb
37
+ - lib/gogogibbon/config.rb
38
+ - lib/gogogibbon/methods.rb
39
+ - lib/gogogibbon/version.rb
40
+ homepage: http://github.com/GoGoCarl/gogogibbon
41
+ licenses: []
42
+ metadata: {}
43
+ post_install_message:
44
+ rdoc_options: []
45
+ require_paths:
46
+ - lib
47
+ required_ruby_version: !ruby/object:Gem::Requirement
48
+ requirements:
49
+ - - ">="
50
+ - !ruby/object:Gem::Version
51
+ version: '0'
52
+ required_rubygems_version: !ruby/object:Gem::Requirement
53
+ requirements:
54
+ - - ">="
55
+ - !ruby/object:Gem::Version
56
+ version: '0'
57
+ requirements: []
58
+ rubyforge_project:
59
+ rubygems_version: 2.7.6
60
+ signing_key:
61
+ specification_version: 4
62
+ summary: Useful helpers for Gibbon
63
+ test_files: []