effective_mailchimp 0.11.6 → 0.12.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 CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: 6afb847e3f7b4628213327ca6c8c7784ec5e1bca4a8e9d04c2ba85b455889aef
4
- data.tar.gz: 1215e45d2068ac5d3af1218365e3cbd0542e3e67238d3b62830d89310c3a7fe8
3
+ metadata.gz: ce289e932fc39342dcbff540f77bada053331d81b67a5f3019df23e0ab49abd7
4
+ data.tar.gz: d2e848d52d61cfec67c5207f31587c172893c5f57579206aa4fc6ccb94ab04c9
5
5
  SHA512:
6
- metadata.gz: 53d077c387dbac60d2c5a6f65156f3116cd8e0ffe36544289a3ea663d81c32e635a2ef29e28e29fa886db8c0734f88f527a6220f093a42aa933479ad9d5c0c9c
7
- data.tar.gz: 266964e54de1dd3f909a36c92f97285de938752b83a396b908f56ff4b97c9979caada46d790f634f4712cd3aeaf297738ac8bbde77b7f27d5f492d6c0e0d5635
6
+ metadata.gz: 62c87c42fdb6aa97b30907fbfcf290501a0c8a6dea93f592871f37e9302f354c160328e484fa819d8d890ab814194c320856381ca7702768ea670b021611e9d1
7
+ data.tar.gz: 015a77c5faa0159784b5e45aba1c4ca72310ec07ab67811317cddf5705dea67702558a6564f32b9fc9963f86149bdcc2f2dc26e6d503d58bd293db420ac74283
@@ -45,7 +45,9 @@ module Admin
45
45
 
46
46
  EffectiveResources.authorize!(self, :update, resource)
47
47
 
48
+ api = EffectiveMailchimp.api
48
49
  resource.mailchimp_sync!
50
+ resource.mailchimp_update!
49
51
 
50
52
  flash[:success] = "Successfully synced mailchimp"
51
53
 
@@ -7,7 +7,9 @@ module Effective
7
7
 
8
8
  EffectiveResources.authorize!(self, :mailchimp_sync_user, current_user)
9
9
 
10
- resource.mailchimp_sync!
10
+ api = EffectiveMailchimp.api
11
+ resource.mailchimp_sync!(api: api)
12
+ resource.mailchimp_update!(api: api)
11
13
 
12
14
  flash[:success] = "Successfully synced mailchimp"
13
15
 
@@ -12,6 +12,7 @@ class EffectiveMailchimpSyncUsersJob < ApplicationJob
12
12
  begin
13
13
  puts "Mailchimp sync user #{user.id}"
14
14
  user.mailchimp_sync!(api: api)
15
+ user.mailchimp_update!(api: api)
15
16
  rescue => e
16
17
  EffectiveLogger.error(e.message, associated: user) if defined?(EffectiveLogger)
17
18
  ExceptionNotifier.notify_exception(e, data: { user_id: user.id }) if defined?(ExceptionNotifier)
@@ -21,8 +21,6 @@ module EffectiveMailchimpUser
21
21
  end
22
22
 
23
23
  included do
24
- attr_accessor :mailchimp_user_form_action
25
-
26
24
  has_many :mailchimp_list_members, -> { Effective::MailchimpListMember.sorted }, as: :user, class_name: 'Effective::MailchimpListMember', dependent: :destroy
27
25
  accepts_nested_attributes_for :mailchimp_list_members, allow_destroy: true
28
26
 
@@ -70,7 +68,6 @@ module EffectiveMailchimpUser
70
68
  end
71
69
 
72
70
  # This sets up the after_commit to run the mailchimp_update! job
73
- assign_attributes(mailchimp_user_form_action: true)
74
71
  save!
75
72
  end
76
73
 
@@ -86,8 +83,6 @@ module EffectiveMailchimpUser
86
83
  end
87
84
 
88
85
  # This sets up the after_commit to run the mailchimp_update! job
89
- assign_attributes(mailchimp_user_form_action: true)
90
-
91
86
  save!
92
87
  end
93
88
 
@@ -166,6 +161,10 @@ module EffectiveMailchimpUser
166
161
  periods.compact.max
167
162
  end
168
163
 
164
+ def mailchimp_cannot_be_subscribed?
165
+ mailchimp_list_members.any?(&:cannot_be_subscribed?)
166
+ end
167
+
169
168
  def mailchimp_subscribed_lists
170
169
  mailchimp_list_members.select(&:subscribed?).map(&:mailchimp_list)
171
170
  end
@@ -206,8 +205,6 @@ module EffectiveMailchimpUser
206
205
  def mailchimp_sync!(api: EffectiveMailchimp.api)
207
206
  lists = Effective::MailchimpList.sorted.to_a
208
207
 
209
- assign_attributes(mailchimp_user_form_action: nil)
210
-
211
208
  mailchimp_with_retries do
212
209
  Timeout::timeout(lists.length * 3) do
213
210
  lists.each do |mailchimp_list|
@@ -224,7 +221,7 @@ module EffectiveMailchimpUser
224
221
  member.mark_for_destruction unless list.present?
225
222
  end
226
223
 
227
- save!
224
+ without_mailchimp_update_async { save! }
228
225
  end
229
226
 
230
227
  def mailchimp_update_async!
@@ -235,8 +232,6 @@ module EffectiveMailchimpUser
235
232
  # Pushes the current Mailchimp List Member objects to Mailchimp when needed
236
233
  # Called in the background after a form submission that changes the user email/last_name/first_name or mailchimp subscriptions
237
234
  def mailchimp_update!(api: EffectiveMailchimp.api, only: [], except: [])
238
- assign_attributes(mailchimp_user_form_action: nil)
239
-
240
235
  return if mailchimp_member_update_blocked?
241
236
 
242
237
  mailchimp_list_members.each do |member|
@@ -254,18 +249,25 @@ module EffectiveMailchimpUser
254
249
  rescue MailchimpMarketing::ApiError => e
255
250
  message = e.to_s.downcase
256
251
 
257
- if message.include?("cannot be subscribed") || message.include?("deleted") || message.include?("unsubscribed")
252
+ if message.include?("cannot be subscribed") || message.include?("deleted") || message.include?("unsubscribed") || message.include?("archived") || message.include?("cleaned")
258
253
  member.assign_mailchimp_cannot_be_subscribed
259
- elsif message.include?("already a list member")
254
+ elsif message.include?("already a list member") || message.include?("already in this list")
260
255
  existing = api.list_member(member.mailchimp_list, member.user.email)
261
256
  member.assign_mailchimp_attributes(existing) if existing.present?
257
+ elsif message.include?("could not be found")
258
+ # Nothing to do
262
259
  else
263
- raise(e)
260
+ # Nothing to do.
264
261
  end
262
+
263
+ if defined?(ExceptionNotifier) && !EffectiveMailchimp.silence_api_errors?
264
+ ExceptionNotifier.notify_exception(e, data: { user_id: id || 'nil' })
265
+ end
266
+
265
267
  end
266
268
  end
267
269
 
268
- save!
270
+ without_mailchimp_update_async { save! }
269
271
  end
270
272
 
271
273
  # Subscribe to force_subscribe lists
@@ -276,6 +278,19 @@ module EffectiveMailchimpUser
276
278
  mailchimp_subscribe!(mailchimp_lists)
277
279
  end
278
280
 
281
+ def without_mailchimp_update_async(&block)
282
+ raise('expected a block') unless block_given?
283
+
284
+ before = @mailchimp_member_update_enqueued
285
+
286
+ begin
287
+ @mailchimp_member_update_enqueued = true
288
+ yield
289
+ ensure
290
+ @mailchimp_member_update_enqueued = before
291
+ end
292
+ end
293
+
279
294
  private
280
295
 
281
296
  def mailchimp_with_retries(retries: 3, wait: 2, &block)
@@ -300,14 +315,16 @@ module EffectiveMailchimpUser
300
315
  def mailchimp_member_update_required?
301
316
  return false unless EffectiveMailchimp.api_present?
302
317
 
303
- return false unless mailchimp_user_form_action
304
- return false if self.class.respond_to?(:effective_memberships_user) && membership&.mailchimp_membership_update_required?
318
+ #return false if self.class.respond_to?(:effective_memberships_user) && membership&.mailchimp_membership_update_required?
305
319
 
306
320
  # Update if my email first name or last name change
307
321
  require_update = self.class.require_mailchimp_update_fields()
308
322
  return true if (changes.keys & require_update).present?
309
323
  return true if (previous_changes.keys & require_update).present?
310
324
 
325
+ # Update if any of my addresses change
326
+ return true if addresses.any? { |a| a.changes.present? || a.previous_changes.present? || a.marked_for_destruction? }
327
+
311
328
  # Update if any of my mailchimp list members changed
312
329
  # which happens when I submit a form and change the Mailchimp values
313
330
  return true if mailchimp_list_members.any? { |m| m.changes.present? || m.previous_changes.present? || m.marked_for_destruction? }
@@ -108,8 +108,8 @@ module Effective
108
108
  def add_merge_field(id, name:, type: :text)
109
109
  raise("invalid mailchimp merge key: #{name}. Must be 10 or fewer characters") if name.to_s.length > 10
110
110
 
111
- return if sandbox_mode?
112
111
  Rails.logger.info "[effective_mailchimp] Add List Merge Field #{name}" if debug?
112
+ return if sandbox_mode?
113
113
 
114
114
  payload = { name: name.to_s.titleize, tag: name.to_s, type: type }
115
115
 
@@ -124,8 +124,8 @@ module Effective
124
124
  def list_member_add(member)
125
125
  raise('expected an Effective::MailchimpListMember') unless member.kind_of?(Effective::MailchimpListMember)
126
126
 
127
- return if sandbox_mode?
128
127
  Rails.logger.info "[effective_mailchimp] Add List Member" if debug?
128
+ return if sandbox_mode?
129
129
 
130
130
  # See if they exist somehow
131
131
  existing = list_member(member.mailchimp_list, member.user.email)
@@ -143,8 +143,8 @@ module Effective
143
143
  def list_member_update(member)
144
144
  raise('expected an Effective::MailchimpListMember') unless member.kind_of?(Effective::MailchimpListMember)
145
145
 
146
- return if sandbox_mode?
147
146
  Rails.logger.info "[effective_mailchimp] Update List Member" if debug?
147
+ return if sandbox_mode?
148
148
 
149
149
  payload = list_member_payload(member)
150
150
  client.lists.update_list_member(member.mailchimp_list.mailchimp_id, member.email, payload)
@@ -1,4 +1,8 @@
1
1
  = card('Mailchimp') do
2
+ - if user.mailchimp_cannot_be_subscribed?
3
+ .alert.alert-warning.mb-3
4
+ This user has been marked as a Compliance State by Mailchimp and cannot be subscribed.
5
+
2
6
  %p.text-muted
3
7
  = succeed('.') do
4
8
  = user
@@ -1,11 +1,6 @@
1
1
  - user = f.object
2
2
 
3
3
  - if user.persisted?
4
- - if user.mailchimp_list_members.any?(&:cannot_be_subscribed?)
5
- %p.text-danger
6
- %small
7
- This user has been marked as a Compliance State by Mailchimp and cannot be subscribed.
8
-
9
4
  %p.text-muted
10
5
  %small
11
6
  last synced with
@@ -1,5 +1,3 @@
1
- = f.hidden_field :mailchimp_user_form_action, value: true
2
-
3
1
  = f.fields_for :mailchimp_list_members, f.object.build_mailchimp_list_members do |fmlm|
4
2
  - mailchimp_list = fmlm.object.mailchimp_list
5
3
  - next if mailchimp_list.blank?
@@ -11,4 +11,6 @@ EffectiveMailchimp.setup do |config|
11
11
 
12
12
  # Assign the User class name. For use in determining all merge_fields
13
13
  # config.user_class_name = 'User'
14
+
15
+ config.silence_api_errors = false
14
16
  end
@@ -1,3 +1,3 @@
1
1
  module EffectiveMailchimp
2
- VERSION = '0.11.6'.freeze
2
+ VERSION = '0.12.0'.freeze
3
3
  end
@@ -9,7 +9,7 @@ module EffectiveMailchimp
9
9
  [
10
10
  :mailchimp_lists_table_name, :mailchimp_list_members_table_name, :mailchimp_categories_table_name, :mailchimp_interests_table_name,
11
11
  :layout,
12
- :api_key, :sandbox_mode, :user_class_name
12
+ :api_key, :sandbox_mode, :user_class_name, :silence_api_errors
13
13
  ]
14
14
  end
15
15
 
@@ -39,6 +39,10 @@ module EffectiveMailchimp
39
39
  Effective::MailchimpList.all.count == 0
40
40
  end
41
41
 
42
+ def self.silence_api_errors?
43
+ !!silence_api_errors
44
+ end
45
+
42
46
  def self.User
43
47
  klass = user_class_name.constantize if user_class_name.present?
44
48
  klass ||= Tenant.User if defined?(Tenant)
@@ -57,7 +61,7 @@ module EffectiveMailchimp
57
61
  end
58
62
 
59
63
  def self.permitted_params
60
- [ :mailchimp_user_form_action, mailchimp_list_members_attributes: [:id, :mailchimp_list_id, :subscribed, interests: []] ]
64
+ [ mailchimp_list_members_attributes: [:id, :mailchimp_list_id, :subscribed, interests: []] ]
61
65
  end
62
66
 
63
67
  # Used to supress any background jobs during import processes
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: effective_mailchimp
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.11.6
4
+ version: 0.12.0
5
5
  platform: ruby
6
6
  authors:
7
7
  - Code and Effect
8
8
  autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
- date: 2025-05-06 00:00:00.000000000 Z
11
+ date: 2025-12-18 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: rails